Date : 2019/10/10
Degree of difficulty:Universal
Original question:P2404 自然数的拆分问题
这道题用的还是dfs
只不过需要考虑三个问题
- 递归的是什么
- 如何去重
- 输出的问题
1.递归
我们可以在dfs函数中写两个变量一个t一个sum
sum等于给定值时退出
我们这样来搞
void dfs(int t,int sum){//递归的是和
if(sum == n && jud(t)){//输出时用jud去重
???//输出的地方
}
for(int i = 1; i < n;i++){
if(sum+i<=n){
a[t]=i;
sum+=i;
dfs(t+1,sum);
sum-=i;
}
}
}
2.去重
去重可以在dfs函数中写
也可以在输出的时候判断
(写一个函数判断是不是数组中每一个数都大于等于前一个数即可)
dfs中版本
外加函数版本
很简单但是很有效,不需要多思考
bool jud(int t){//判断去重的一个函数,我太弱了
for(int i = 1; i <= t-1; i ++){
if(a[i]<a[i-1]) return 0;
}
return 1;
}
3.输出
输出挺好搞的
AC code
dfs 记得return!!
#include<bits/stdc++.h>
using namespace std;
int n,sum a[25];
bool b[25];
bool jud(int t){//判断去重的一个函数,我太弱了
for(int i = 1; i <= t-1; i ++){
if(a[i]<a[i-1]) return 0;
}
return 1;
}
void dfs(int t,int sum){//递归的是和
if(sum == n && jud(t)){//输出时用jud去重
for(int i = 1; i < t-1; i ++){
printf("%d+",a[i]);
}
printf("%d\n",a[t-1]); //前两行的目的是中间输出加号,后面换行
return;//void 一定要返回 !!
}
for(int i = 1; i < n;i++){
if(sum+i<=n){
a[t]=i;
sum+=i;
dfs(t+1,sum);
sum-=i;
}
}
}
int main() {
scanf("%d",&n);
dfs(1,0);
return 0;
}