ICPC Arab Collegiate Programming Contest 2014 C题
题解:转化为因子考虑,因为每一种选取相同的个数
#include <bits/stdc++.h>
using namespace std;
typedef long long LL;
const LL maxn=5005+10;
const LL maxm=55;
const LL mod=1e9+7;
LL S,N;
LL V[maxn],C[maxn];
LL f[maxm][maxn];
int mp[maxn];
int main()
{
int T;
scanf("%d",&T);
int c=1;
while(T--){
scanf("%lld%lld",&S,&N);
for(LL i=1;i<=N;i++){
scanf("%lld%lld",&V[i],&C[i]);
}
memset(mp,0,sizeof(mp));
vector<LL> v;v.clear();
for(LL i=1;i<=S;i++){
if(S%i==0){
if(mp[i]==0){
mp[i]=1;
v.push_back(i);
}
}
}
LL res=0;
LL n=v.size();
for(LL k=0;k<n;k++){
LL m=v[k];
memset(f,0,sizeof(f));
for(LL i=1;i<=N;i++){
for(LL j=1;j<=m;j++){
LL l=S/m;
if(j-V[i]>=0&&f[i-1][j-V[i]]&&l*V[i]<=S&&l<=C[i]){//一定要加l<=C[i],否则会wa
f[i][j]+=f[i-1][j-V[i]];
}
f[i][j]+=f[i-1][j];
if(l<=C[i]&&V[i]==j&&l*V[i]<=S){
f[i][j]+=1;
}
}
}
/*for(LL i=1;i<=N;i++){
for(LL j=1;j<=m;j++){
printf("%lld ",f[i][j]);
}
printf("\n");
}*/
res+=f[N][m];
}
if(S==0){
res=1;
}
printf("Case %d: %lld\n",c++,res);
}
return 0;
}