离散化+深搜。
对给出的n个数排序,然后离散,求出每个数有多少个,然后递归判断每个数出现多少次时 能使和等于sum,需要注从大数开始深搜。。
代码:
# include<stdio.h>
# include<string.h>
# include<stdlib.h>
int a[20],b[20],c[20],sum,ans,flag,ys;
int cmp(const void *a,const void *b)
{
return *(int *)b - *(int *)a;
}
void dfs(int i)
{
int j,k,h;
for(j=b[i];j>=0;j--)
{
ans+=a[i]*j;
c[i]=j;
if(ans>sum)
{
ans-=a[i]*j;
continue;
}
if(ans==sum)
{
flag=0;
for(k=1;k<=i;k++)
{
for(h=1;h<=c[k];h++)
{
if(flag==0) {printf("%d",a[k]);flag=1;}
else printf("+%d",a[k]);
}
}
printf("\n");
ans-=a[i]*j;
continue;
}
if(i==ys) {ans-=a[i]*j;return;}
dfs(i+1);
ans-=a[i]*j;
}
}
int main()
{
int i,n;
while(scanf("%d%d",&sum,&n)!=EOF)
{
if(sum==0 && n==0) break;
for(i=1;i<=n;i++)
scanf("%d",&a[i]);
qsort(a+1,n,sizeof(a[1]),cmp);
memset(b,0,sizeof(b));
ys=1;
b[ys]=1;
for(i=2;i<=n;i++)
{
if(a[i]==a[i-1]) b[ys]++;
else
{
ys++;
a[ys]=a[i];
b[ys]=1;
}
}
ans=0;
flag=0;
printf("Sums of %d:\n",sum);
dfs(1);
if(flag==0) printf("NONE\n");
}
return 0;
}