组合数学实验——生成{1,2,……,n}的组合的基2算法

同前几篇博客

算法:组合数学中文第4版 机械工业出版社 P64

//////////////////////////////////////////////
//                                          //
//  Project Name: combination               //
//                                          //
//  File Name: combination.h                //
//                                          //
//  Author: Victor Zhang                    //
//                                          //
//  ID: 21*****92                           //
//                                          //
//  Create Date: March 25. 2009             //
//                                          //
//////////////////////////////////////////////

#ifndef COMBINATION_H
#define COMBINATION_H

#define COMMAX 20

struct unit
{
	unit* pre;
	bool data[COMMAX];
	int id;
	unit* next;
};

class Combination
{
private: 
	unit* tail;
	int setNum;
	int unitNum;

//	bool deleteUnit(unit*);
	bool addUnit(unit*, int);
public:
	Combination(int n);
	Combination()
	{
		tail = NULL;
		setNum = unitNum = 0;
	};
	~Combination()
	{
		deleteAll();
		tail = NULL;
		setNum = 0;
	};
//	bool addData(int);
	bool renewData(int);
	bool deleteAll();
	void process();
	void prtQueue();
};

#endif
//////////////////////////////////////////////
//                                          //
//  Project Name: combination               //
//                                          //
//  File Name: combination.cpp              //
//                                          //
//  Author: Victor Zhang                    //
//                                          //
//  ID: 21*****92                           //
//                                          //
//  Create Date: March 25. 2009             //
//                                          //
//////////////////////////////////////////////

#include <iostream>

using namespace std;

#include "combination.h"

Combination::Combination(int n)
{
	this->tail = NULL;
	this->setNum = n;
	if (!(this->renewData(n)))
	{
		this->deleteAll();
		this->setNum = 0;
	};
};

bool Combination::renewData(int n)
{
	this->tail = NULL;
	this->setNum = 0;
	int r_unitNum = 0;
	r_unitNum = (n / COMMAX) + 1;
	if (!(this->addUnit(tail, r_unitNum))) return false;
	int i = 0;
	int j = 0;
	unit* p;
	p = this->tail;
	for (i = 0; i < r_unitNum; i++)
	{
		if (p)
		{
			p->id = i;
			if (i == (r_unitNum - 1))
			{
				for (j = 0; j < COMMAX; j++)
				{
					if ((i*COMMAX + j + 1) > n) p->data[j] = true;
				};
			};
			p = p->pre;
		};
	};
	this->unitNum = r_unitNum;
	this->setNum = n;
	return true;
};

bool Combination::addUnit(unit* a_tail, int n)
{
	unit* tmp_tail = this->tail;
	tail = a_tail;
	unit* a_next;
	a_next = a_tail;
	int i = 0;
	int j = 0;
	for (i = 0; i < n; i++)
	{
		unit* p = new unit;
		if (!(p))
		{
			this->deleteAll();
			this->tail = tmp_tail;
			return false;
		};
		p->pre = NULL;
		for (j = 0; j < COMMAX; j++)
		{
			p->data[j] = false;
		};
		p->next = a_next;
		if (a_next)
		{
			a_next->pre = p;
		}
		else
		{
			this->tail = p;
		};
		a_next = p;
	};
	return true;
};

bool Combination::deleteAll()
{
	unit* p;
	while(this->tail)
	{
		p = this->tail->pre;
		delete tail;
		this->tail = p;
	};
	return true;
};

void Combination::process()
{
	while (1)
	{
		//find
		if (!this->tail) return;
		unit* p = this->tail;
		int j = 0;
		while (p)
		{
			for (j = 0; j < COMMAX; j++)
			{
				if (!(p->data[j])) break;
			};
			if ((j < COMMAX) && !(p->data[j])) break;
			p = p->pre;
		};
		//~find
	
		//print
		this->prtQueue();
		//~print
	
		//not find
		if (!(p)) return;
		//~not find
	
		//change
		int i = p->id;
		unit* pp = this->tail;
		int jj = 0;
		while ((pp) && (pp->id <= i))
		{
			for (jj = 0; jj < COMMAX; jj++)
			{
				if ((pp == p) && (jj == j))
				{
					pp->data[jj] = true;
					break;
				};
				pp->data[jj] = false;
			};
			if ((pp == p) && (jj == j)) break;
			pp = pp->pre;
		};
		//~change
	};
};

void Combination::prtQueue()
{
	if (!(this->tail)) return;
	unit* p;
	int i = 0;
	bool empty = true;
	p = this->tail;
	while (p)
	{
		for (i = 0; i < COMMAX; i++)
		{
			if ((p->data[i]) && (((p->id) * COMMAX + i + 1) <= this->setNum))
			{
				cout<<((p->id) * COMMAX + i + 1)<<" ";
				empty = false;
			};
		};
		p = p->pre;
	};
	if (empty) cout<<"<Empty>";
	cout<<endl;
};
//////////////////////////////////////////////
//                                          //
//  Project Name: combination               //
//                                          //
//  File Name: main.cpp                     //
//                                          //
//  Author: Victor Zhang                    //
//                                          //
//  ID: 21*****92                           //
//                                          //
//  Create Date: March 25. 2009             //
//                                          //
//////////////////////////////////////////////

#include <iostream>

using namespace std;

#include "combination.h"

void main()
{
	cout<<"Please input a NUMBER:";
	int i;
	cin>>i;
	Combination a(i);
	a.process();
	system("pause");
};

你可能感兴趣的:(组合,组合数学)