关闭

地图染色问题(回溯法)

标签: 回溯法地图染色
662人阅读 评论(0) 收藏 举报
分类:

1.问题描述:

对图G共分成n个顶点,有m种颜色,现在要对其进行作色,要求相邻的顶点不能染相同的颜色.

2.算法设计:

  • 对于给定无向连通图G 可用邻接矩阵表示,该邻接矩阵用一个二维数组表示,其中为了直观,第0行和第0列全赋值为0,不参与算法.
如邻接矩阵 a[i][j],若a[1][2]=1;则表示地图1区域和2区域(相邻)连通,不难知道 a[2][1]也为1.  若i,j不相邻,则a[i][j] = a[j][i]=0.

  • 关于不同地图区域的着色,可以用一维数组x[i]表示,如: x[3]=2; 表示第3块区域着第2号色.
3.解空间:

用一颗高度为n+1的m叉树,即表示每个结点有m种着色选择.


  • 用回溯法Backtrack(i) 按深度遍历搜索,当找到第n+1层,即i>n,表示找到一个解决方案,注意只有符合条件查找才会继续.
  • 代码示例:

#include<iostream>
using namespace std;
class Color{
	friend int mColoring(int,int, int **);	//友元函数声明
private:
	bool OK(int k);
	void Backtrack(int t);
	int n,			//顶点数
		m,			//颜色数
		* * a,		//图的邻接矩阵,记录相邻顶点
		* x;		//当前解, x[2]=3;表示第二个点染3号色
		long sum;	//记录截至当前解决方案个数
};

bool Color::OK(int k)//函数定义
{//查看是否符合条件
	for(int j=1;j<=n;j++)
		if( (a[k][j]==1)&&(x[k]==x[j]) )//即第k个和第j个相邻且染同色(在邻接矩阵里有边的点不能染同色)
			return false;
	return true;	//此处不可写else 必须走完j,和所有相邻的点检测一遍
}

void Color::Backtrack(int t)
{
	if(t>n){
		sum++;//解决方案++ 拓展至子结点
		cout<<"染色方案_"<<sum<<":\t";
		for (int i = 1; i <=n; i++) //输出解决方案
			cout<<x[i]<<" ";			
		cout<<endl;
	}
	else 
		for (int i = 1; i <=m; i++)	//每种颜色都试下
		{
			x[t]=i;					//尝试染色
			if(OK(t))Backtrack(t+1);//if:ok 递归进入下一个
			x[t]=0;
		}
}

//-------------------------------------------------------------
int mColoring(int n,int m, int **a)	//调用函数
{
	Color X;
	X.n=n;
	X.m=m;
	X.a=a;	//邻接矩阵
	X.sum=0;	//解决方案初始化0

	int *p = new int [n+1];	//当前解初始化;
	for (int i = 0; i <=n; i++)		//即使第0个不用,亦初始化
		p[i]=0;
	X.x = p;	//x指向p 共享一块空间
	X.Backtrack(1);
	delete []p;	//删除数组
	return X.sum;
}
//------------------------------------------------------
void Show_TheMap(int **p, int n)//输出邻接矩阵
	{
		int i,j;
		cout<<"该图邻接矩阵如下:\n";
		for (i = 1; i <=n; i++)
			for (j = 1; j <=n; j++)
			{
				cout<<p[i][j]<<" ";
				if(j==n)	cout<<endl;
			}
	}
void main()
{	
	int **a = new int *[6];				//第0个不存,只存 邻接矩阵:1-5行 1-5列
	for (int i = 0; i < 6; i++)
	{
		a[i] = new int[6];
	}
//邻接矩阵初始化
	for (int i = 1; i < 6; i++)
		for(int j=1;j < 6; j++)
			a[i][j]=1;
	for(int i=1;i<6;i++)
		a[i][i]=0;	//对角线初始化为0,其余初始化为1;	此处为测试例子		
	a[3][5]=a[5][3]=0;a[1][5]=a[5][1]=0;	//表示1-3,5-3不相邻

	Show_TheMap(a,5);
	cout<<endl;
	cout<<"共有"<<mColoring(5,4,a)<< " 个染色方案"<< endl;	//调用
	
}




程序结果示例:



该算法引用自:《计算机算法设计与分析》————电子工业出版社p137-p139

0
0
查看评论

022-3着色问题-回溯法-《算法设计技巧与分析》M.H.A学习笔记

一个无向图G,用三种颜色给顶点着色,使得邻接的顶点颜色不相同。
  • qq_18738333
  • qq_18738333
  • 2016-06-29 16:45
  • 2214

回溯法---->图的着色问题

图的着色问题 1、问题描述 图的m-着色判定问题——给定无向连通图G和m种不同的颜色。用这些颜色为图G的各顶点着色,每个顶点着一种颜色,是否有一种着色法使G中任意相邻的2个顶点着不同颜色? 图的m-着色优化问题——若一个图最少需要m种颜色才能使图中任意相邻的2个顶点着不同颜色,则称这个数m为该...
  • ncepustrong
  • ncepustrong
  • 2013-05-16 10:12
  • 1640

回溯法 图着色问题

问题:给定 无向连通图G=(V,E) 和 c种不同的颜色,用这些颜色为图G的各顶点着色,每个顶点着一种颜色。如果一个图最少需要c种颜色才能使图中每条边连接的2个顶点着不同颜色,则称c为该图的色数。 著名的 四色定理 就是指每个平面地图都可以只用四种颜色来染色,而且没有两个邻接的区域颜色相同。求:给...
  • jeffleo
  • jeffleo
  • 2017-01-17 19:42
  • 601

地图染色问题

四色定理是一个著名的数学定理:如果在平面上划出一些邻接的有限区域,那么可以用四种颜色来给这些区域染色,使得每两个邻接区域染的颜色都不一样[2][3];另一个通俗的说法是:每个(无飞地的)地图都可以用不多于四种颜色来染色,而且不会有两个邻接的区域颜色相同。被称为邻接的两个区域是指它们有一段公共的边界,...
  • yichao_ding
  • yichao_ding
  • 2014-10-23 13:30
  • 760

图着色问题 配色方案 C++实现 回溯法

/* 函数功能:求解图着色问题 * 作者 :王宇虹 * 时间 :2015年5月21日 12:02:00.000 * 编译环境:Dec-C++ 5.8.3 */ #include #include using namespace std; int n,m,g,i; ...
  • wyh7280
  • wyh7280
  • 2015-05-21 13:12
  • 1359

回溯经典-m图着色问题(和地图4色问题的区别)

四色问题:四色问题是m图着色问题的一个特列,根据四色原理,证明平面或球面上的任何地图的所有区域都至多可用四种、颜色来着色,并使任何两个有一段公共边界的相邻区域没有相同的颜色。这个问题可转换成对一平面图的4-着色判定问题(平面图是一个能画于平面上而边无任何交叉的图)。将地图的每个区域变成一个结点,若两...
  • suwei19870312
  • suwei19870312
  • 2010-02-02 22:05
  • 14328

回溯法-3着色问题

一、3着色问题     给定无向连通图G和m种不同的颜色。用这些颜色为图G的各顶点着色,每个顶点着一种颜色。是否有一种着色法使G中每条边的2个顶点着不同颜色。这个问题是图的m可着色判定问题。若一个图最少需要m种颜色才能使图中每条边连接的2个顶点着不同颜色,则称这个...
  • Sylvia3130
  • Sylvia3130
  • 2017-03-21 14:46
  • 1024

地图染色问题——四色问题

地图染色
  • mangoer_ys
  • mangoer_ys
  • 2014-05-28 09:38
  • 1877

染色问题的算法

#include #define NUM 5 using namespace  std;   bool ok(int i,int b[],int a[NUM][NUM]) { for(int j=0;j   if(a[i][j]==1&&...
  • u013861473
  • u013861473
  • 2014-05-18 19:22
  • 976

poj 2777 Count Color(线段树+染色问题)

Count Color Chosen Problem Solving and Program design as an optional course, you are required to solve all kinds of problems. Here, we get a new probl...
  • qiqi_skystar
  • qiqi_skystar
  • 2015-12-20 16:10
  • 1175
    个人资料
    • 访问:12658次
    • 积分:461
    • 等级:
    • 排名:千里之外
    • 原创:33篇
    • 转载:0篇
    • 译文:0篇
    • 评论:0条
    文章分类