1. 程式人生 > >Codeforces Round #360 C

Codeforces Round #360 C

!= sin end mod contest log mes name linker

NP-Hard Problem

題意:給一個圖,問能否把每條邊的2端放在2個不同的集合裏

思路:暴搜01染色,以顏色做為標記每次搜索的時候可以遍歷到一個聯通塊裏的所有邊,但是註意在搜索的時候如果發現下一個點已經被染色了,那麽在退出這層搜索前需要判斷一下下一個點的顏色是否和當前點的顏色一樣

AC代碼:

#include "iostream"
#include "string.h"
#include "stack"
#include "queue"
#include "string"
#include "vector"
#include "set"
#include "map"
#include 
"algorithm" #include "stdio.h" #include "math.h" #pragma comment(linker, "/STACK:102400000,102400000") #define ll long long #define bug(x) cout<<x<<" "<<"UUUUU"<<endl; #define mem(a,x) memset(a,x,sizeof(a)) #define mp(x,y) make_pair(x,y) #define pb(x) push_back(x) #define lrt (rt<<1) #define
rrt (rt<<1|1) using namespace std; const long long INF = 1e18+1LL; const int inf = 1e9+1e8; const int N=1e5+100; const ll mod=1e9+7; ///CCCC int cl[N<<1],vis[N<<1],nex[N<<2],head[N<<1],to[N<<1],id[N<<1],tot,flag,ans[3]; void add(int u, int v){ to[tot]=v; nex[tot]
=head[u]; head[u]=tot++; } void dfs(int u,int c){ //bug("xx") if(cl[u]==c){ flag=1; return; } cl[u]=c^1; ans[c^1]++; for(int i=head[u]; i!=-1; i=nex[i]){ int v=to[i]; if(cl[v]!=-1){ if(cl[u]==cl[v]){ flag=1; return; } continue; } dfs(v,cl[u]); } } int main(){ int n,m,u,v; cin>>n>>m; mem(head,-1), mem(cl,-1); for(int i=1; i<=m; ++i){ cin>>u>>v; add(u,v); add(v,u); id[u]=1; id[v]=1; } for(int i=1; i<=n; ++i){ //cout<<cl[i]<<" "<<id[i]<<"\n"; if(cl[i]==-1 && id[i]==1) dfs(i,1); if(flag){ cout<<"-1\n"; return 0; } } cout<<ans[0]<<"\n"; for(int i=1; i<=n; ++i){ if(id[u] && cl[i]==0){ cout<<i<<" "; } } cout<<"\n"; cout<<ans[1]<<"\n"; for(int i=1; i<=n; ++i){ if(id[u] && cl[i]==1){ cout<<i<<" "; } } return 0; }

Codeforces Round #360 C