某财务部门结账时发现总金额不对头。很可能是从明细上漏掉了某一笔或几笔。如果已知明细账目清单,能通过编程找到漏掉的是哪一笔或几笔吗?如果有种可能,则输出所有可能的情况。我们规定,用户输入的第一行是:有错的总金额。接下来是一个整数n,表示下面将要输入的明细账目的条数。再接下来是n行整数,分别表示每笔账目的金额。要求程序输出:所有可能漏掉的金额组合。每个情况一行。金额按照从小到大排列,中间用空格分开。比如,用户输入:
6
5
3
2
4
3
1
则输出
1 3 3
1 2 4
3 4
编程思想:简单递归。
CODE:
#include<stdio.h>
#include<iostream>
#include<cstring>
#include<math.h>
#include<algorithm>
using namespace std;
int a[1000],mark[1000];
void f(int err_sum,int a[],int cur_sum,int n,int k)
{
if(err_sum<cur_sum) return;
if(err_sum==cur_sum)
{
for(int i=0;i<n;i++)
{
if(mark[i]==0)
{
printf("%d ",a[i]);
}
}
puts("");
return;
}
if(k>=n) return;
/* 与下面的等价
for(int i=k;i<n;i++)
{
mark[i]=1;
cur_sum+=a[i];
f(err_sum,a,cur_sum,n,i+1);
mark[i]=0;
cur_sum-=a[i];
}*/
mark[k]=0;
f(err_sum,a,cur_sum,n,k+1);
mark[k]=1;
cur_sum+=a[k];
f(err_sum,a,cur_sum,n,k+1);
mark[k]=0;
cur_sum-=a[k];
}
int main()
{
int err_sum,cur_sum,n,i;
while(scanf("%d",&err_sum)!=EOF)
{
scanf("%d",&n);
for(i=0;i<n;i++)
{
scanf("%d",&a[i]);
}
sort(a,a+n);
memset(mark,0,sizeof(mark));
f(err_sum,a,0,n,0);
}
return 0;
}