zoukankan      html  css  js  c++  java
  • 图的M着色问题

    问题描述:

      给定无向连通图 G 和 m 种不同的颜色。用这些颜色为图 G 和各顶点着色,每个顶点着一种颜色。是否有一种着色法使得图 G 中每条边的两个顶点着不同的颜色。这个问题是图的 m 可着色判定问题。若一个图最少需要 m 种颜色才能使图中的每条边连接的两个顶点着不同的颜色,则称这个数 m 为该图的色数。求一个图的色数 m 的问题称为图的 m 可着色优化问题。

      四色问题是m图着色问题的一个特例,根据四色原理,证明平面或球面上的任何地图的所有区域都至多可用四种、颜色来着色,并使任何两个有一段公共边界的相邻区域没有相同的颜色。这个问题可将平面图转换成对平面点的着色判定问题,将地图的每个区域变成一个结点,若两个区域相邻,则相应的结点用一条边连接起来。如将五个区域换成用点的方式表示,如下图:

    即用矩阵的表示如下:

     

     用回溯法解空间,先假设三种颜色和三个点,解空间如下:


    package com.calculateprogram;
    /**
     * 图的M上着色问题
     * @author 郭庆兴
     *
     */
    public class NColoring {
    	static int n,	//图的顶点数
    	m;	//可用的颜色数
    	static boolean [][]a;	//图的邻接矩阵,表示点与点之间是否的连接
    	static int []x;			//当前解
    	static long sum;		//当前找到的可着色的方案数
    
    	public static long NColoring(int nColor){
    		m=nColor;
    		sum=0;
    		backtrace(1);
    		return sum;
    	}
    
    
    	private static void backtrace(int i) {
    		if (i>n) {
    			//当最后一个点被着色后,此时i大于n,即所有点已染色完成
    			sum++;
    			//打印出此种方案的结果
    			System.out.print("第"+sum+"种方案(点数从1依次到5涂上颜色):");
    			for (int j = 1; j <= n; j++) 
    				System.out.print(x[j]+" ");
    			System.out.println();
    		}
    		else 
    			//开始给一个点添加颜色,同时判断其可行性,
    			for (int j = 1; j <= m ; j++) {
    				//给改点图上m号颜色
    				x[i]=j;
    				//若此种颜色可行,即执行进行深层次的着色
    				if (ok(x[i])) 
    					backtrace(i+1);
    				//将该点恢复到原来的状态
    				x[i]=0;
    			}
    
    	}
    
    
    
    	private static boolean ok(int i) {
    		// 检查颜色的可行性
    		for (int j = 1; j <= n; j++) 
    			if (a[i][j] && (x[j]==x[i]) ) 
    				return false;
    			
    			return true;
    
    	}
    
    
    	public static void main(String[] args) {
    		n=5;
    		m=4;
    		x=new int[6];
    		a=new boolean[6][6];
    		for (int i = 0; i < a.length; i++)
    			for (int t = 0; t < a.length; t++)
    				a[i][t]=false;
    		a[1][2]=true;a[1][3]=true;a[1][4]=true;
    		a[2][1]=true;a[2][3]=true;a[2][5]=true;a[2][4]=true;
    		a[3][1]=true;a[3][2]=true;a[3][4]=true;
    		a[4][1]=true;a[4][2]=true;a[4][3]=true;a[4][5]=true;
    		a[5][2]=true;a[5][4]=true;
    		backtrace(1);
    	}
    }
    

      程序结果如图:

      

  • 相关阅读:
    vxlan简介1
    什么underlay网络?
    CDN:内容分发网络
    zz博通发布用于数据中心交换机的开源软件开发套件SDKLT
    DPDK盒子使用手册——DPDK入门zz
    2018年最值得关注的15大技术趋势zz
    为什么要使用叶脊(leaf-spine)拓扑网络zz
    openvswitch
    Linux基础训练题型(下)
    Linux基础命令训练题型(上)
  • 原文地址:https://www.cnblogs.com/helloworldcode/p/6905955.html
Copyright © 2011-2022 走看看