1154 Vertex Coloring (25分)
A proper vertex coloring is a labeling of the graph’s vertices with colors such that no two vertices sharing the same edge have the same color. A coloring using at most k colors is called a (proper) k-coloring.
Now you are supposed to tell if a given coloring is a proper k-coloring.
Input Specification:
Each input file contains one test case. For each case, the first line gives two positive integers N and M (both no more than 104), being the total numbers of vertices and edges, respectively. Then M lines follow, each describes an edge by giving the indices (from 0 to N−1) of the two ends of the edge.
After the graph, a positive integer K (≤ 100) is given, which is the number of colorings you are supposed to check. Then K lines follow, each contains N colors which are represented by non-negative integers in the range of int. The i-th color is the color of the i-th vertex.
Output Specification:
For each coloring, print in a line k-coloring if it is a proper k-coloring for some positive k, or No if not.
題目翻譯:
1154 頂點着色
“proper vertex coloring”是用顏色標記圖形的頂點,使得共享相同邊緣的兩個頂點具有不同顏色。使用至多k種顏色的着色稱爲“k-coloring”。
現在你需要指出給定的着色是否是“k-coloring”。
輸入格式:
每個輸入文件包含一個測試用例。對於每個測試用例,第一行給出兩個正整數N和M(均不超過10 ^ 4),分別代表頂點和邊的總數。然後是M行,每行都通過給出邊兩端的索引(從0到N-1)來描述邊。
在描述完邊的信息之後,給出一個正整數K(<= 100),這是你需要檢查的着色數量。然後緊跟着K行,每行包含N個顏色,這些顏色由int範圍內的非負整數表示。第i種顏色表示第i個頂點的顏色。
Sample Input:
10 11 //N個頂點,M條邊
8 7 //每條邊起始頂點
6 8
4 5
8 4
8 1
1 2
1 4
9 8
9 1
1 0
2 4
4 //需要判斷以下四種情況是幾着色
0 1 0 1 4 1 0 1 3 0 //本行意思:例第八個頂點是第三個顏色
0 1 0 1 4 1 0 1 0 0
8 1 0 1 4 1 0 5 3 0
1 2 3 4 5 6 7 8 8 9
Sample Output:
4-coloring
No
6-coloring
No
題目解析:
我覺得此題看懂題幹就是一個難點,我個渣渣結合翻譯軟件還看了好長時間才明白(555555…)
看懂以後要想清楚用哪些數據結構存儲數據。因爲這題裏又有邊又有點。
1.剛開始邊的個數未知,可以用變長數組vector存儲.
2.每個點的顏色,由於要統計“幾着色問題(顏色個數)”,所以可以用set存儲顏色(set可以去重並且元素遞增)
最後枚舉邊,看邊的頂點顏色是否一致,如果一致則不是n着色問題。
代碼展示:
#include<iostream>
#include<cstdio>
#include<vector>
#include<set>
using namespace std;
struct node
{
int p1,p2;
};
int main()
{
int m,n,k;
cin>>m>>n;//m個點,n條邊
vector<node> bian(n);//必須初始化並且必須用圓括號
for(int i=0;i<n;i++)
{
scanf("%d %d",&bian[i].p1,&bian[i].p2);//scanf讀入時間比cin讀入時間短
}
cin>>k;
while(k>0)
{
int dian[10000]={0};//數組初始化很重要,存儲點的顏色,並且題目要求邊不大於10000
set<int> s;
bool flag=true;
for(int j=0;j<m;j++)
{
scanf("%d",&dian[j]);
s.insert(dian[j]);
}
for(int q=0;q<n;q++)//枚舉n條邊
{
if(dian[bian[q].p1]==dian[bian[q].p2])
{
flag=false;
break;
}
}
if(flag==false)
{
cout<<"No"<<endl;
}
else
{
cout<<s.size()<<"-coloring"<<endl;
}
k--;
}
}
總結
寫這道題可真是累死我了,心態爆炸了。
出現幾個問題
1.存儲點的顏色數組大小必須看題目要求不大於10000,否則發生段錯誤。
2.vector是變長數組,此題需要以數組的方式讀入,需要初始化。初始化必須用圓括號。不是方括號。否則出錯。
3.scanf讀入時間比cin讀入時間短
加油吧,繼續幹。