链接:点击打开链接
这道题如果不是数据超过__int64位的范围就是一道简单的完全背包问题,高精度模拟大数加法,其他的就是完全背包差不多啦。。。
#include<iostream>
#include<stdio.h>
#include<string.h>
using namespace std;
int dp[1010][110];
void ADD(int n,int m){
int i,j;
for(i=0;i<60;i++){
dp[n][i]+=dp[m][i];
if(dp[n][i]>=10){
dp[n][i]%=10;
dp[n][i+1]++;
}
}
}
int main(){
int i,j,n,m;
while(~scanf("%d %d",&n,&m)){
memset(dp,0,sizeof(dp));
dp[0][0]=1;
for(i=1;i<=m;i++)
for(j=i;j<=n;j++)
ADD(j,j-i);
for(j=100;j>=0;j--)
if(dp[n][j]!=0)
break;
for(i=j;i>=0;i--)
printf("%d",dp[n][i]);
printf("\n");
}
return 0;
}
还可以用两个long long数组,一个存低位,一个存高位,这样也可以。。一种很不错的方法,刚学到的。。。
#include<iostream>
#include<stdio.h>
#include<string.h>
using namespace std;
long long a[1010],b[1010];
int main(){
long long INF;
int i,j,n,k;
INF=1;
for(i=1;i<=18;i++)
INF*=10;
while(~scanf("%d %d",&n,&k)){
memset(a,0,sizeof(a));
memset(b,0,sizeof(b));
b[0]=1;
for(i=1;i<=k;i++)
for(j=i;j<=n;j++){
a[j]=a[j]+a[j-i]+(b[j]+b[j-i])/INF;
b[j]=(b[j]+b[j-i])%INF;
}
if(a[n])
printf("%I64d",a[n]);
printf("%I64d\n",b[n]);
}
return 0;
}