算法分析与设计复习-回溯法和分支限界法

// 回溯法 and 分支限界法 : 解空间搜索技术 
#include 
//三着色问题:每次只产生一个子节点,深度优先;不需要存储整棵树,只需要存储根到当前活动节点的路径。

int[] 3COLORREC(int n)
{
	int c[n];
	for(int k = 1; k <= n; k ++)
		c[k] = 0;
	bool flag = false;
	graphcolor(1);
	if(flag)
		for(int i = 1; i <= n ; i ++)
		{
			printf("%d ",c[i]);
		}
	else
		printf("no solution\n");
} 

void graphcolor(int k)
{
	for(int color = 1; color<=3; color++)
	{
		c[k] = color;
		if(c合法着色)  
		{
			flag = true;
			break;
		}
		else if(c是部分的)
			graphcolor(k+1);
	}
}

void 3COLORITER()
{
	for(int k = 1; k <= n; k++)
		c[k] = 0;
	bool flag = false;
	int k =1;
	while(k >= 1)
	{
		while(c[k] <= 2)
		{
			c[k] = c[k] +1;
			if(c合法着色)
			{
				flag = true;
				break;   //从两个循环中跳出 
			}
			else if(c是部分解)
				k = k+1; 
		}
		c[k] = 0;
		k = k-1;  //回溯 
	}
	if(flag ) 
		输出c 
}
 
//PARTITION问题:给定一个集合X={x1,x2,...xn}和整数Y,找出和等于y的X的子集。
/*x[i]为0/1, w[i]为具体的数值 
取第k+1个数的限制条件: 
1. SUM (w(i)*x(i) i:1~k)  + SUM(w(i) i:k+1~n) >= Y 
2. 假定w(i)已经按照升序排号后,SUM (w(i)*x(i) i:1~k) + w(k+1) <= Y
*/ 

int M;
int x[];
int w[];

//r = w[1] + w[2] + ... + w[n]  PART(s,1,r)

//s 前k个数的和   r w[k]+...+w[n]的和 
int PART(int s,int k, int r)
{
	x[k] = 1;
	// 刚好划分成功了 
	if(s + w[k] = M)
	{
		//flag = true;
		for(int i = 0; i < n; i ++)
		{
			printf("%d ",w[i]);
		} 
	}
	else
	{
		if(s + w[k] + w[k+1] <= M)
			PART(s+w[k],k+1,r-w[k]);
	}
	
	if(s + r -w[k] >= M && s+w[k+1] <= M)
	{
		x[k] = 0;
		PART(s,k+1,r-w[k]);
	}
} 


//分支限界法:关心使给定的函数最大化或者最小化,算法为每一节点x计算一个界,若比以前的界限更坏,不会再以x为根生成子节点。


你可能感兴趣的:(算法分析与设计复习-回溯法和分支限界法)