题目描述
设集合S={x1,x2,…,xn}是一个正整数集合,c是一个正整数,子集和问题判定是否存在S的一个子集S1,使S1中的元素之和为c。试设计一个解子集和问题的回溯法。
输入格式:
输入数据第1行有2个正整数n和c,n表示S的大小,c是子集和的目标值。接下来的1行中,有n个正整数,表示集合S中的元素。
输出格式:
输出子集和问题的解,以空格分隔,最后一个输出的后面有空格。当问题无解时,输出“No Solution!”。
输入样例:
5 10 2 2 6 5 4
输出样例:
2 2 6
参考代码:
#include<bits/stdc++.h>
#define N 10001
using namespace std;
int n,c,sum,flag;
//n表示S的大小,c是子集和的目标值
//sum是当前子集和的值,flag用于标志结果
int s[N];//元素的集合
bool ss[N];//表示是否包含当前元素
void search(int i){
if(i>n){//下标超过集合的大小
return;
}
//取数
ss[i]=true;
sum+=s[i];
if(sum==c){//满足情况
flag=1;
for(int j=0;j<=i;j++){
if(ss[j]){
cout << s[j] << " ";
}
}
exit(0);//退出函数
}
else if(sum<c){//继续取数
search(i+1);
}
//回溯
ss[i]=false;
sum-=s[i];
search(i+1);
}
int main(){
cin >> n >> c;
int count=0;
for(int i=0;i<n;i++){
cin >> s[i];
count+=s[i];//求集合元素的总和
}
if(count<c){//不加会超时
cout << "No Solution!" << endl;
return 0;
}
search(0);
if(!flag){
cout << "No Solution!" << endl;
}
return 0;
} 
京公网安备 11010502036488号