AcWing
  • 首页
  • 课程
  • 题库
  • 更多
    • 竞赛
    • 题解
    • 分享
    • 问答
    • 应用
    • 校园
  • 关闭
    历史记录
    清除记录
    猜你想搜
    AcWing热点
  • App
  • 登录/注册

洛谷 P2404. 自然数的拆分问题    原题链接    简单

作者: 作者的头像   flowerhy ,  2024-08-04 16:18:47 ,  所有人可见 ,  阅读 27


2


自然数的拆分问题

题目描述

任何一个大于 $1$ 的自然数 $n$,总可以拆分成若干个小于 $n$ 的自然数之和。现在给你一个自然数 $n$,要求你求出 $n$ 的拆分成一些数字的和。每个拆分后的序列中的数字从小到大排序。然后你需要输出这些序列,其中字典序小的序列需要优先输出。

输入格式

输入:待拆分的自然数 $n$。

输出格式

输出:若干数的加法式子。

样例 #1

样例输入 #1

7

样例输出 #1

1+1+1+1+1+1+1
1+1+1+1+1+2
1+1+1+1+3
1+1+1+2+2
1+1+1+4
1+1+2+3
1+1+5
1+2+2+2
1+2+4
1+3+3
1+6
2+2+3
2+5
3+4

提示

数据保证,$2\leq n\le 8$。


算法1

(DFS)

“每个拆分后的序列中的数字从小到大排序。”

因为是组合,所以我们保证后一个数大于等于前一个数。

for(int i=1;i<=n;i++){   
    a[i]=i;      //每一种拆分方案由该数开始
    dfs(n-i,1);  //继续拆分剩下的数
}
void dfs(int x,int cnt){
    if(x == 0)   //当 x=0时表示找到了一组拆分方案
    {
       cout<<a[0];
       for(int i=1;i<cnt;i++)
       cout<<"+"<<a[i];

       cout<<endl;
    }

    //继续拆分剩下的数
    for(int i=a[cnt-1];i<x;i++){     //后一个数大于等于前一个数
        a[cnt]=i;
        dfs(x-i,cnt+1);
    }
}

C++ 代码

#include <bits/stdc++.h>
using namespace std;

const int N = 40;
int n;
int a[N];

void dfs(int x,int cnt){
    if(x == 0)  //找到一组拆分 
    {
        printf("%d",a[0]);

        for(int i=1;i < cnt;i++)
        printf("+%d",a[i]); 

        puts("");
    }

    //继续拆分
    for(int i = a[cnt-1];i<=x;i++) {
        a[cnt] = i;
        dfs(x-i,cnt+1);
    }
}
int main(){
    scanf("%d",&n);

    for(int i=1;i<n;i++){
         a[0]=i;           
         dfs(n-i,1);      
    }
    return 0; 
}

1 评论


用户头像
wanbinan   2025-03-21 10:39 · 江苏         踩      回复

大佬写的很好理解


App 内打开
你确定删除吗?
1024
x

© 2018-2025 AcWing 版权所有  |  京ICP备2021015969号-2
用户协议  |  隐私政策  |  常见问题  |  联系我们
AcWing
请输入登录信息
更多登录方式: 微信图标 qq图标 qq图标
请输入绑定的邮箱地址
请输入注册信息