球盒问题之三:n分解成m个正数和所有组合
来源:互联网 发布:sql注入漏洞怎么修复 编辑:程序博客网 时间:2024/04/29 11:21
球盒问题之三:n分解成m个正数和所有组合
问题
将正整数n分解成m个正整数之和,给出所有组合。此问题等同于等同于n个球放到m个盒子中,盒子不能为空,球与盒子都完全相同。
算法
这个问题并不难,只要把去重的问题解决,基本都能给出正确的算法。
此处用有序数列的方式给出一种算法。不保证算法很高效啊。:)。如有更好的算法,请推荐下啊。
用有序数列来解决去重的问题,即得出的结果用一个二维数组保存,一行为一个结果,但保证每行中的数都是按从小到大或者从大到小的顺序排列,且各行不相同。如此,写一个从1开始遍历到n/m的循环,然后每层均进行递归。
部分代码
代码如下:
std::vector<std::vector<int> > Permute::sumNToDst(int dst, int n){ std::vector<std::vector<int> > r; findUpSeq(1,n,dst,r); std::cout<<r.size()<<" solutions "<<std::endl; for(int i=0;i<r.size();i++){ for(int j=0;j<r.at(i).size();j++){ std::cout<<r.at(i).at(j)<<" "; } std::cout<<std::endl; }}/** * @brief Permute::findUpSeq * @param low 盒子中最少放置的球数 * @param num 盒子数 * @param sum 球总数 * @param result 返回二维数组分配结果 * @return 是否分配成功 */int Permute::findUpSeq(int low, int num,int sum, vector<vector<int> > &result){ result.clear(); if(num<1||sum<0) return 0; //只有一个盒子 if(num==1){ if(sum>=low){ std::vector<int> v; v.push_back(sum); result.push_back(v); return 1; } return 0; }else if(num<1){ return 0; } //球数少于每个盒子应放总数之和 if(sum<num*low) return 0; else if(sum == num*low){ std::vector<int> t; t.assign(num,low); result.push_back(t); return low; } std::vector<std::vector<int> > s; //依次给1号盒子放1-n/m个球,将剩下的球放到剩下的盒子中且保证后续盒子球数不低于前一盒子 for(int i=low;((i*num)<sum+1);i++){ s.clear(); //如果后续盒子放置成功,将其放置方案中加入1号盒子中所放球数做为一个方案 if(findUpSeq(i,num-1,sum-i,s)){ for(int j=0;j<s.size();j++){ s.at(j).push_back(i); result.push_back(s.at(j)); for(int k=0;k<s.at(j).size();k++){ std::cout<<" "<<s.at(j).at(k); } } std::cout<<std::endl; } } return 1;}
测试
测试代码:
Permute per;per.sumNToDst(25,5);
测试结果
192 solutions 21 1 1 1 1 20 2 1 1 1 19 3 1 1 1 18 4 1 1 1 17 5 1 1 1 16 6 1 1 1 15 7 1 1 1 14 8 1 1 1 13 9 1 1 1 12 10 1 1 1 11 11 1 1 1 19 2 2 1 1 18 3 2 1 1 17 4 2 1 1 16 5 2 1 1 15 6 2 1 1 14 7 2 1 1 13 8 2 1 1 12 9 2 1 1 11 10 2 1 1 17 3 3 1 1 16 4 3 1 1 15 5 3 1 1 14 6 3 1 1 13 7 3 1 1 12 8 3 1 1 11 9 3 1 1 10 10 3 1 1 15 4 4 1 1 14 5 4 1 1 13 6 4 1 1 12 7 4 1 1 11 8 4 1 1 10 9 4 1 1 13 5 5 1 1 12 6 5 1 1 11 7 5 1 1 10 8 5 1 1 9 9 5 1 1 11 6 6 1 1 10 7 6 1 1 9 8 6 1 1 9 7 7 1 1 8 8 7 1 1 18 2 2 2 1 17 3 2 2 1 16 4 2 2 1 15 5 2 2 1 14 6 2 2 1 13 7 2 2 1 12 8 2 2 1 11 9 2 2 1 10 10 2 2 1 16 3 3 2 1 15 4 3 2 1 14 5 3 2 1 13 6 3 2 1 12 7 3 2 1 11 8 3 2 1 10 9 3 2 1 14 4 4 2 1 13 5 4 2 1 12 6 4 2 1 11 7 4 2 1 10 8 4 2 1 9 9 4 2 1 12 5 5 2 1 11 6 5 2 1 10 7 5 2 1 9 8 5 2 1 10 6 6 2 1 9 7 6 2 1 8 8 6 2 1 8 7 7 2 1 15 3 3 3 1 14 4 3 3 1 13 5 3 3 1 12 6 3 3 1 11 7 3 3 1 10 8 3 3 1 9 9 3 3 1 13 4 4 3 1 12 5 4 3 1 11 6 4 3 1 10 7 4 3 1 9 8 4 3 1 11 5 5 3 1 10 6 5 3 1 9 7 5 3 1 8 8 5 3 1 9 6 6 3 1 8 7 6 3 1 7 7 7 3 1 12 4 4 4 1 11 5 4 4 1 10 6 4 4 1 9 7 4 4 1 8 8 4 4 1 10 5 5 4 1 9 6 5 4 1 8 7 5 4 1 8 6 6 4 1 7 7 6 4 1 9 5 5 5 1 8 6 5 5 1 7 7 5 5 1 7 6 6 5 1 6 6 6 6 1 17 2 2 2 2 16 3 2 2 2 15 4 2 2 2 14 5 2 2 2 13 6 2 2 2 12 7 2 2 2 11 8 2 2 2 10 9 2 2 2 15 3 3 2 2 14 4 3 2 2 13 5 3 2 2 12 6 3 2 2 11 7 3 2 2 10 8 3 2 2 9 9 3 2 2 13 4 4 2 2 12 5 4 2 2 11 6 4 2 2 10 7 4 2 2 9 8 4 2 2 11 5 5 2 2 10 6 5 2 2 9 7 5 2 2 8 8 5 2 2 9 6 6 2 2 8 7 6 2 2 7 7 7 2 2 14 3 3 3 2 13 4 3 3 2 12 5 3 3 2 11 6 3 3 2 10 7 3 3 2 9 8 3 3 2 12 4 4 3 2 11 5 4 3 2 10 6 4 3 2 9 7 4 3 2 8 8 4 3 2 10 5 5 3 2 9 6 5 3 2 8 7 5 3 2 8 6 6 3 2 7 7 6 3 2 11 4 4 4 2 10 5 4 4 2 9 6 4 4 2 8 7 4 4 2 9 5 5 4 2 8 6 5 4 2 7 7 5 4 2 7 6 6 4 2 8 5 5 5 2 7 6 5 5 2 6 6 6 5 2 13 3 3 3 3 12 4 3 3 3 11 5 3 3 3 10 6 3 3 3 9 7 3 3 3 8 8 3 3 3 11 4 4 3 3 10 5 4 3 3 9 6 4 3 3 8 7 4 3 3 9 5 5 3 3 8 6 5 3 3 7 7 5 3 3 7 6 6 3 3 10 4 4 4 3 9 5 4 4 3 8 6 4 4 3 7 7 4 4 3 8 5 5 4 3 7 6 5 4 3 6 6 6 4 3 7 5 5 5 3 6 6 5 5 3 9 4 4 4 4 8 5 4 4 4 7 6 4 4 4 7 5 5 4 4 6 6 5 4 4 6 5 5 5 4 5 5 5 5 5
0 0
- 球盒问题之三:n分解成m个正数和所有组合
- 球盒问题之二:n分解成m正数和解题代码
- //组合问题(从M个不同字符中任取N个字符的所有组合)
- 组合问题(从M个不同字符中任取N个字符的所有组合)
- 组合问题(从M个不同字符中任取N个字符的所有组合)
- 组合问题(从M个不同字符中任取N个字符的所有组合)
- 组合问题:从M个字符取N个不同字符所有组合
- OJ 系列之从M个不同字符中任取N个字符的所有组合
- 从m个字符选出n个的所有组合
- java实现从M个元素中取N个元素的所有组合(数学中的组合问题)
- 给定2个数字,n,m,使得从1到n之间的数字组合,他们的和等于m,求所有组合
- 组合问题:全组合和C(n,m)
- N个鸡蛋放入M个篮子且能组合出1~N所有的数
- 求从1,2...n中取任意个不重复的数和为m的所有组合
- 组合问题——从n种球种取出m个
- 关于数学组合问题在m个球中取n个球-递归实现
- 所有组合, 所有排列的模板(从n个数中选m个数的所有组合和所有排列)
- m选n组合问题
- Android 自定义view探索
- 同时安装office2016与visio2016
- 第十六周2
- 股票入门基础知识1:什么是股票和股份?
- 编译原理之小记录
- 球盒问题之三:n分解成m个正数和所有组合
- [BZOJ1385][Baltic2000]Division expression
- (八)适配器模式详解
- 稀疏矩阵相乘——三元组稀疏矩阵
- no qualifying bean of type found for dependen
- Android 系统源码编译
- 蓝桥杯(Java )基础练习 数列排序
- JS中encodeURIComponent(URL)编码与decodeURIComponent(URL)解码详解
- 国外程序员整理的 C++ 资源大全