P1:按题意有两种构造方法,只需要比较哪种代价更小就可以了。
object Solution {
def movesToMakeZigzag(A: Array[Int]): Int = {
def f(i:Int):Int = {
A.indices.toList
.filter(_%2 == i)
.map{x =>
0 max (List(x-1, x+1) filter A.indices.contains map A map (y => A(x) - y + 1) max)}
.sum
}
f(0) min f(1)
}
}
P2: 在选手一选完之后, 选手二只能有三种选择方式:记选手选择xxx, 选手二的选择,只能是x的父节点,左节点,或者右节点。 这样做能让压缩选手一的最后结果。 所以,只要比较这三种的最大值是否存在一个值比整棵树的一半大即可。
object Solution {
def btreeGameWinningMove(root: TreeNode, n: Int, x: Int): Boolean = find(root,x) match {
case node =>
(count(node), count(node.left), count(node.right)) match {
case (m, m_l, m_r) => List(n-m, m_l, m_r).max > n /2
}
}
def count(root:TreeNode):Int = root match {
case null => 0
case _ => count(root.left) + count(root.right) + 1
}
def find(root:TreeNode, x:Int):TreeNode = {
if(root == null) null
else if(root.value == x) root
else find(root.left, x) match {
case null => find(root.right, x)
case node => node
}
}
}
Update: 这里用match case总感觉不大优雅。于是,有了下面一段代码。对一个变量不能用map,就放到了list里面。还是觉得不大好。 试着用compose,andThen去组合逻辑,又显得代码太多,有点难看。
object Solution {
def btreeGameWinningMove(root: TreeNode, n: Int, x: Int): Boolean = {
List(find(root,x)) flatMap { x:TreeNode =>
List(n-count(x), count(x.left), count(x.right))
} exists (_>n/2)
}
def count(root:TreeNode):Int = root match {
case null => 0
case _ => count(root.left) + count(root.right) + 1
}
def find(root:TreeNode, x:Int):TreeNode = root match {
case null => null
case _ if root.value == x => root
case _ => find(root.left, x) match {
case null => find(root.right, x)
case node => node
}
}
}
P3: 这题显然不能直接开空间, 想到用Hash做就很简单了。
class SnapshotArray(_length: Int) {
var snap_id = 0
val table = scala.collection.mutable.HashMap[(Int, Int), Int]() // (Snap_id, index) => value
def set(index: Int, x: Int) {
table.put((snap_id, index), x)
}
def snap(): Int = {
snap_id += 1
snap_id -1
}
def get(index: Int, id: Int): Int = {
if(id == -1) 0
else {
if(table.contains((id, index))) table((id,index))
else get(index,id-1)
}
}
}
P4: 贪心,一个从左, 一个从右,尽可能少的选择块数,是的两个子串相等。应该是简单题,不知道放在最后面。
object Solution {
def longestDecomposition(A: String): Int = {
def f(i:Int, j:Int, acc:Int = 0):Int = {
if(i > j) acc else g(i,j) match {
case n =>
if(j-n+1 == i) f(i+n, j-n, acc+1)
else f(i+n, j-n, acc+2)
}
}
def g(i:Int, j:Int, d:Int = 1 ):Int = {
if(A.substring(i,i+d) == A.substring(j-d+1,j+1)) d
else g(i,j, d+1)
}
f(0, A.length-1, 0)
}
}