LeetCode312
有 n
个气球,编号为0
到 n - 1
,每个气球上都标有一个数字,这些数字存在数组 nums
中。
现在要求你戳破所有的气球。戳破第 i
个气球,你可以获得 nums[i - 1] * nums[i] * nums[i + 1]
枚硬币。 这里的 i - 1
和 i + 1
代表和 i
相邻的两个气球的序号。如果 i - 1
或 i + 1
超出了数组的边界,那么就当它是一个数字为 1
的气球。
求所能获得硬币的最大数量。
示例 1:
输入:nums = [3,1,5,8] 输出:167 解释: nums = [3,1,5,8] --> [3,5,8] --> [3,8] --> [8] --> [] coins = 3*1*5 + 3*5*8 + 1*3*8 + 1*8*1 = 167
示例 2:
输入:nums = [1,5] 输出:10
提示:
n == nums.length
1 <= n <= 300
0 <= nums[i] <= 100
思路:
区间dp
代码:
class Solution {
public:
int maxCoins(vector<int>& nums) {
int dp[305][305];
memset(dp,0,sizeof(dp));
int len=nums.size();
vector<int> v(len+2);
v[0]=v[len+1]=1;
for(int i=1;i<=len;i++)
{
v[i]=nums[i-1];
}
for(int i=len-1;i>=0;i--)
{
for(int j=i+2;j<=len+1;j++)
{
for(int k=i+1;k<j;k++)
{
int sum=v[i]*v[j]*v[k];
sum+=dp[i][k]+dp[k][j];
dp[i][j]=max(dp[i][j],sum);
}
}
}
return dp[0][len+1];
}
};
LeetCode322
给你一个整数数组 coins
,表示不同面额的硬币;以及一个整数 amount
,表示总金额。
计算并返回可以凑成总金额所需的 最少的硬币个数 。如果没有任何一种硬币组合能组成总金额,返回 -1
。
你可以认为每种硬币的数量是无限的。
示例 1:
输入:coins =[1, 2, 5]
, amount =11
输出:3
解释:11 = 5 + 5 + 1
示例 2:
输入:coins =[2]
, amount =3
输出:-1
示例 3:
输入:coins = [1], amount = 0 输出:0
提示:
1 <= coins.length <= 12
1 <= coins[i] <= 231 - 1
0 <= amount <= 104
思路:
背包的个数问题。
代码:
class Solution {
public:
int coinChange(vector<int>& coins, int amount) {
int dp[100005];
memset(dp,9999,sizeof(dp));
int n=coins.size();
dp[0]=0;
for(int i = 1; i <= amount; ++i)
{
for(int j = 0; j < n; ++j)
{
if(coins[j]<=i) dp[i] = min(dp[i],dp[i-coins[j]]+1);
}
}
if(dp[amount]>amount)return -1;
return dp[amount];
}
};