- DFS 遍历每一种情况,时间复杂度很高…
class Solution
{
public:
int findTargetSumWays(vector<int> &nums, int S)
{
if (nums.empty())
return 0;
int res = 0;
helper(nums, 0, 0, S, res);
return res;
}
void helper(vector<int> &nums, int curInx, int curNum, int S, int &count)
{
if (curInx >= nums.size())
{
if (curNum == S)
++count;
return;
}
helper(nums, curInx + 1, curNum + nums[curInx], S, count);
helper(nums, curInx + 1, curNum - nums[curInx], S, count);
}
};
-
DP
设P为nums中所有要取正的数的集合,N为所有要取负的数的集合,target为目标值sum(P) - sum(N) = target sum(P) + sum(N) + sum(P) - sum(N) = target + sum(P) + sum(N) 2 * sum(P) = target + sum(nums)
题目转换成为:求出满足2 * sum(P) = target + sum(nums)
等式的数的P集合
class Solution
{
public:
int getSums(vector<int> vec)
{
int sum = 0;
for (auto n : vec)
sum += n;
return sum;
}
int findTargetSumWays(vector<int> &nums, int S)
{
int sum = getSums(nums);
if (S < -sum || S > sum)
return 0;
//dp[i][j]表示通过使用第i项来达到和j的可能方法的数量
vector<vector<int>> dp(nums.size() + 1, vector<int>(sum * 2 + 1, 0));
dp[0][sum] = 1;
for (int i = 1; i <= nums.size(); i++)
{
for (int j = 0; j <= 2 * sum; j++)
{
if (j + nums[i - 1] <= 2 * sum)
{
dp[i][j] += dp[i - 1][j + nums[i - 1]];
}
if (j - nums[i - 1] >= 0)
{
dp[i][j] += dp[i - 1][j - nums[i - 1]];
}
}
}
return dp[nums.size()][sum + S];
}
};