C语言求组合

引入

假设5个数 1 2 3 4 5,选3个数求组合。可以按如下思路来考虑

  1. 先选取1,从生下的2 3 4 5中选2个求组合,这是一个递归过程
  2. 先选取2,从 3 4 5中选2个求组合,仍旧是一个递归过程
  3. 选取3,从 4 5中选2个求组合
  4. 遇到4,剩下的数字只有1个,不能再选取2个,因此不用继续考虑

定义递归_comb(array, visit, int l, int k)
其中visit是一次递归过程中选取的标记,l是子数列的开始下标,k是需要选取的个数

代码

#include <iostream>
#include <queue>
#include <vector>
#include <functional>

using namespace std;

void _comb(vector <int> &array, vector <int> &visit, vector <vector <int>> &result, int l, int k)
{
	visit[l] = 1;

	if(k == 1) {
		vector <int> tmp;

		for(int i=0; i<visit.size(); i++) {
			if(visit[i]) {
				tmp.push_back(array[i]);
			}
		}

		result.push_back(tmp);
		visit[l] = 0;
		return;
	}

	for(int i=l+1; i<array.size() && (l+k) <= array.size(); i++) {
		_comb(array, visit, result, i, k-1);
	}

	visit[l] = 0;
}

void comb(vector <int> &array, vector <vector <int>> &result, int k)
{
	int n = array.size();
	vector <int> visit;

	visit.resize(n);
	for(int i=0; i<n; i++) {
		visit[i] = 0;
	}


	for(int i=0; i<n; i++) {
		_comb(array, visit, result, i, k);
	}
}

int main(void)
{
	vector <int> array;
	vector <vector <int>> result;

	for(int i=0; i<5; i++) {
		array.push_back(i+1);
	}

	comb(array, result, 2);

	for(int i=0; i<result.size(); i++) {
		for(int j=0; j<result[i].size(); j++) {
			cout << result[i][j] << " ";
		}
		cout << endl;
	}

	return 0;
}

组合

根据上面的排列代码,可以很容易改为组合,组合有两个注意点:
1) 组合要排序,因此需要传入一个vecotr,用来记录访问过的数字
2) 内存递归调用时,不在从下一个开始,而是从0开始

void _paile(vector <int> &array, vector <int> &visit, vector <int> &item, vector <vector <int>> &result, int l, int k)
{
	visit[l] = 1;
	item.push_back(array[l]);

	if(k == 1) {
		result.push_back(item);
		visit[l] = 0;
		item.pop_back();
		return;
	}

	for(int i=0; i<array.size(); i++) {
		if(visit[i] == 0) {
			_paile(array, visit, item, result, i, k-1);
		}
	}

	visit[l] = 0;
	item.pop_back();
}

void pailie(vector <int> &array, vector <vector <int>> &result, int k)
{
	int n = array.size();
	vector <int> visit;
	vector <int> items;

	visit.resize(n);
	for(int i=0; i<n; i++) {
		visit[i] = 0;
	}


	for(int i=0; i<n; i++) {
		_paile(array, visit, items, result, i, k);
	}
}
posted @ 2020-02-07 17:42  joechow  阅读(929)  评论(0)    收藏  举报