问题描述
笔记
设置buff[i]为考虑第i个到最后一个硬币,先手的人能拿到的硬币最大价值和对手的硬币最大价值。sum[i]为第i个到最后一个硬币的总价值。
那么,当前情况我可以拿1个或者2个。
1. 拿1个,我先得到values[i]的价值,对方就得到buff[i+1]的价值,我就再得到sum[i+1]-buff[i+1]的价值;
2. 拿2个,我先得到values[i]+values[i+1]的价值,对方得到buff[i+2]的价值,我再得到sum[i+2]-buff[i+2]的价值。
3. 那我肯定取这两者的最大值。
状态转移方程:
buff[i] = max((values[i] + (sum[i+1] - buff[i+1]), values[i]+values[i+1]+sum[i+2]-buff[i+2])
注意
又用到了从后往前算的小技巧!要记住这个小技巧!
代码
class Solution {
public:
/**
* @param values: a vector of integers
* @return: a boolean which equals to true if the first player will win
*/
bool firstWillWin(vector<int> &values) {
// write your code here
const int len = values.size();
if (len == 1 || len == 2)
return true;
vector<int> buff(len, 0);
vector<int> sum(len, 0);
buff[len-1] = values[len-1];
sum[len-1] = values[len-1];
buff[len-2] = values[len-1] + values[len-2];
sum[len-2] = buff[len-2];
for (int i = len-3; i >= 0; i--)
{
sum[i] = sum[i+1] + values[i];
buff[i] = max(values[i]+sum[i+1]-buff[i+1], values[i]+values[i+1]+sum[i+2]-buff[i+2]);
}
return (buff[0] > (sum[0]-buff[0]));
}
};