回溯法图着色问题递归回溯

View Code
#include<iostream>
using namespace std;
#define N 100
int x[N];//x[i]存储当前i节点的颜色种类 
int a[N][N];//存储各个顶点之间的连接情况 
int sum=0;//记录有多少种涂色方案 

bool OK(int k,int n){
    for(int j=1;j<=n;j++)
        if(a[k][j]==1&&x[j]==x[k])//如果找到一个与预想把K节点涂色为x[k]的相连节点,且该节点也涂色为x[k],则涂色失败 
          return false;
      return true; //找不到则可以涂色 
}
void Backtrack(int t,int n,int m){//深度优先搜索 
    if(t>n){//如果当前节点已经为叶节点 
        sum++;//涂色种类加一
        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,n))
               Backtrack(t+1,n,m);
            x[t]=0;//递归回溯时,把所有节点的涂色清空 
        }
    }
}
int main(){
    int n,//顶点个数
        m;//颜色种类
    x[0]=0;
    cout<<"请输入节点个数:"; cin>>n; 
    cout<<"请输入颜色种类:";cin>>m;
    for(int i=0;i<=n;i++){//先初始化数组的0行0列 
        a[0][i]=0;
        a[i][0]=0;
    }         
    int a1,b1;          
    cout<<"请输入两两相连的两个节点的序号(两个为一组,以(0,0)结束)"<<endl;
     while(a1){
              cin>>a1>>b1;
              a[a1][b1]=1;
              a[b1][a1]=1;
       } 
    Backtrack(1,n,m);
    cout<<"一共有:"<<sum<<"涂色方案"<<endl;
    return 0; 
} 
原文地址:https://www.cnblogs.com/aijianiula/p/2782197.html