Farmer John goes to Dollar Days at The Cow Store and discovers an unlimited number of tools on sale. During his first visit, the tools are selling variously for $1, $2, and $3. Farmer John has exactly $5 to spend. He can buy 5 tools at $1 each or 1 tool at $3 and an additional 1 tool at $2. Of course, there are other combinations for a total of 5 different ways FJ can spend all his money on tools. Here they are:
Input
1 @ US$3 + 1 @ US$2Write a program than will compute the number of ways FJ can spend N dollars (1 <= N <= 1000) at The Cow Store for tools on sale with a cost of $1..$K (1 <= K <= 100).
1 @ US$3 + 2 @ US$1
1 @ US$2 + 3 @ US$1
2 @ US$2 + 1 @ US$1
5 @ US$1
A single line with two space-separated integers: N and K.
Output
A single line with a single integer that is the number of unique ways FJ can spend his money.
Sample Input
5 3Sample Output
5
题解:
完全背包,dp[j]表示凑出j的方案数,dp[j]=dp[j]+dp[j-i],方案数等于不用i的方案数加上用了i的方案数。
只是这个题目会报ll所以要开两个数组分别存前18位和后18位。
代码:
#include <cstdio> #include <iostream> #include <algorithm> #include <cstring> #include <cmath> #include <iostream> #define ll long long #define inf 1000000000000000000 using namespace std; ll dp[2000],f[2000]; int main() { int n,k;scanf("%d%d",&n,&k); dp[0]=1; for(int i=1;i<=k;i++) for(int j=1;j<=n;j++){ if(j<i) continue; f[j]=f[j]+f[j-i]+(dp[j]+dp[j-i])/inf; dp[j]=(dp[j]+dp[j-i])%inf; } if(!f[n]) printf("%lld",dp[n]); else printf("%lld%lld",f[n],dp[n]); return 0; }