中國地圖的四色問題
阿新 • • 發佈:2018-12-10
首先,該問題需要運用到資料結構無向圖的相關知識。
將中國地圖(不包含臺灣、海南)看做是一張無向圖,相鄰接的省份用直線相互連線,就能夠得到一張無向圖。
用鄰接矩陣的方法來儲存該無向圖,相鄰結點對應數字1,不相鄰結點對應數字0。
.然後,在主函式中從一種顏色開始迴圈,直到滿足能用這幾種顏色填滿地圖(方法數不為0)。
for(i=1;i<100;i++)
{
dfs(1,i);
if(WayNumber!=0){
printf("填滿地圖至少需要%d種顏色\n",i);
break;
}
用遞迴的方法進行廣度遍歷,用數字1,2,3,4......表示顏色,構造一個用於存放顏色的陣列area[],
當鄰接矩陣Map[i][j]等於1時,對應的area[i]和area[j]的值不能相同,通過for迴圈從顏色1開始,
不斷進行上色,最終判斷全部結點都已染色時,方法數加1。
for(i=0;i<ColorNumber;i++)
{
int biaoshi=1;
for(j=1;j<youbiao;j++)
{
if((Map[j][youbiao]==1)&&(area[j]==i))
{
biaoshi=0;
break;
}
}
if(biaoshi)
{
area[youbiao]=i; //遊標所在省份染為第i種顏色
}
源程式:
#include <stdio.h>
#include <stdlib.h>#define AREANUMBER 27
int WayNumber=0; //方法數
int Map[AREANUMBER+1][AREANUMBER+1];
int area[AREANUMBER+1];
/*typedef struct ArcNode{
int number; //和該頂點鄰接的頂點編號
struct ArcNode *next; //頂點指向的下一個位置
}ArcNode;
typedef struct{
ArcNode *firstnext; //和該頂點鄰接的第一個頂點編號
}ArcList;
typedef ArcList Map[AREANUMBER]; //地圖的鄰接表陣列
*/
void CreateMap(int Map[AREANUMBER+1][AREANUMBER+1]); //地圖建立函式
void dfs(int now,int ColorNumber); //深度遍歷函式
void main(){
int i,j;
for(i=1;i<=AREANUMBER;i++)
for(j=1;j<=AREANUMBER;j++)
Map[i][j]=0;
CreateMap(Map);
for(i=1;i<100;i++)
{
dfs(1,i);
if(WayNumber!=0){
printf("填滿地圖至少需要%d種顏色\n",i);
break;
}
}
}
void CreateMap(int Map[AREANUMBER+1][AREANUMBER+1]){
/*ArcNode *p,*q;
GL[1].data=1;
p=(ArcNode *)malloc(sizeof(ArcNode));
p->number=3;
p=GL[1].firstnext;
q=(ArcNode *)malloc(sizeof(ArcNode));
q->number=4;
q=p->next;
p=(ArcNode *)malloc(sizeof(ArcNode));
p->number=2;
p=q->next;
*/
Map[1][2]=Map[2][1]=1; //新疆
Map[1][3]=Map[3][1]=1;
Map[1][4]=Map[4][1]=1;
Map[2][4]=Map[4][2]=1; //西藏
Map[2][5]=Map[5][2]=1;
Map[2][10]=Map[10][2]=1;
Map[3][4]=Map[4][3]=1; //甘肅
Map[3][5]=Map[5][3]=1;
Map[3][7]=Map[7][3]=1;
Map[3][8]=Map[8][3]=1;
Map[3][12]=Map[12][3]=1;
Map[4][5]=Map[5][4]=1; //青海
Map[5][6]=Map[6][5]=1; //四川
Map[5][8]=Map[8][5]=1;
Map[5][9]=Map[9][5]=1;
Map[5][10]=Map[10][5]=1;
Map[6][8]=Map[8][6]=1; //重慶
Map[6][9]=Map[9][6]=1;
Map[6][13]=Map[13][6]=1;
Map[6][14]=Map[14][6]=1;
Map[7][8]=Map[8][7]=1; //寧夏
Map[7][12]=Map[12][7]=1;
Map[8][12]=Map[12][8]=1; //陝西
Map[8][14]=Map[14][8]=1;
Map[8][15]=Map[15][8]=1;
Map[8][16]=Map[16][8]=1;
Map[9][10]=Map[10][9]=1; //貴州
Map[9][11]=Map[11][9]=1;
Map[9][13]=Map[13][9]=1;
Map[10][11]=Map[11][10]=1; //雲南
Map[11][26]=Map[26][11]=1; //廣西
Map[11][13]=Map[13][11]=1;
Map[12][15]=Map[15][12]=1; //內蒙古
Map[12][17]=Map[17][12]=1;
Map[12][18]=Map[18][12]=1;
Map[12][19]=Map[19][12]=1;
Map[12][20]=Map[20][12]=1;
Map[13][14]=Map[14][13]=1; //湖南
Map[13][24]=Map[24][13]=1;
Map[13][26]=Map[26][13]=1;
Map[14][16]=Map[16][14]=1; //湖北
Map[14][22]=Map[22][14]=1;
Map[14][24]=Map[24][14]=1;
Map[15][16]=Map[16][15]=1; //山西
Map[15][17]=Map[17][15]=1;
Map[16][17]=Map[17][16]=1; //河南
Map[16][21]=Map[21][16]=1;
Map[16][22]=Map[22][16]=1;
Map[17][20]=Map[20][17]=1; //河北
Map[17][21]=Map[21][17]=1;
Map[18][19]=Map[19][18]=1; //黑龍江
Map[19][20]=Map[20][19]=1; //吉林
//遼寧
Map[21][23]=Map[23][21]=1; //山東
Map[22][23]=Map[23][22]=1; //安徽
Map[22][24]=Map[24][22]=1;
Map[22][25]=Map[25][22]=1;
Map[23][25]=Map[25][23]=1; //江蘇
Map[24][25]=Map[25][24]=1; //江西
Map[24][26]=Map[26][24]=1;
Map[24][27]=Map[27][24]=1;
Map[25][27]=Map[27][25]=1; //浙江
Map[26][27]=Map[27][26]=1; //廣東
//福建
}
void dfs(int youbiao,int ColorNumber){
int i,j,k;
for(i=0;i<ColorNumber;i++)
{
int biaoshi=1;
for(j=1;j<youbiao;j++)
{
if((Map[j][youbiao]==1)&&(area[j]==i)) //遊標所在省與j省鄰接,且j省被染為第i種顏色
{
biaoshi=0;
break;
}
}
if(biaoshi)
{
area[youbiao]=i; //遊標所在省份染為第i種顏色
if(youbiao==AREANUMBER) //全部結點都已染色
WayNumber++; //方法數+1
else
dfs(youbiao+1,ColorNumber); //下一個省份染色
}
}
}