四色图
Description
?Perfectxx給LZH出了一道題,要LZH構造出一個盡可能大的四色圖。所謂的四色圖指的是由n個點m條邊組成的無向圖。其中,每個點要么是紅色,要么是藍色,每條邊要么是黑色,要么是白色。
黑邊能連接兩個紅點,或是一個紅點與一個藍點。而白邊只能連接紅點與藍點。
LZH構造出了一個圖,但是委托給Murphyc,讓他去打印的時候,Murphyc用了黑白打印機。現在分不清楚頂點的顏色是紅還是藍。
現在你需要幫Perfectxx檢查一下,LZH構造出的圖有沒有可能是四色圖。
Input
第一行輸入n和m,表示點的數量和邊的數量?(1<=n,m<=2e5)
接下來的m行,每行三個輸入?w u v?表示圖中有一條從u到v的無向邊,w=1時表示
這條邊是黑邊,w=0是表示這條邊是白邊。
Output
僅輸出一行字符串,其中”Maybe”表示原圖有可能是四色圖,”Impossible”表示原圖一定不是四色圖。(輸出中沒有引號)
Sample Input
4 4 0 1 2 0 2 3 0 3 4 0 4 1 3 3 0 1 2 0 2 3 0 3 1Sample Output
Maybe ImpossibleHINT
題解:
#include<bits/stdc++.h> using namespace std; const int N=500000; int ins[N],dfn[N],low[N],cnt,sta[N]; int top,v,u; int Next[N],head[N],to[N]; int tot; int scc[N]; int scccnt; void make_list(int u,int v){Next[++tot]=head[u],head[u]=tot,to[tot]=v; } void tarjan(int x){ins[x]=dfn[x]=low[x]=++cnt,sta[top++]=x;for(int p=head[x],v=to[p];p;p=Next[p],v=to[p])if(!dfn[v])tarjan(v),low[x]=min(low[x],low[v]);else if(ins[v])low[x]=min(low[x],dfn[v]);if(low[x]==dfn[x]){scc[x]=++scccnt,ins[x]=0;while((u=sta[--top])!=x)ins[u]=0,scc[u]=scccnt;} } int main(){int n,m,w,u,v;freopen("data5.in","r",stdin);freopen("data5.out","w",stdout); scanf("%d%d",&n,&m); for(int i=1;i<=m;i++){scanf("%d%d%d",&w,&u,&v);if(!w){make_list(u,v+n);make_list(v,u+n);make_list(u+n,v);make_list(v+n,u);}else{make_list(u+n,v);make_list(v+n,u);}}for(int i=1;i<=2*n;i++){if(!dfn[i])tarjan(i);}bool ok=1;for(int i=1;i<=n;i++){ok&=(scc[i]!=scc[i+n]);}if(ok)puts("Maybe");else puts("Impossible");return 0; }?
總結