【结论】欧拉路+并查集——hdu3018

对于一个连通图而言,有这样的一个性质:其需要画的笔数=度数为奇数的点数除以2

有了这个结论,用并查集求联通块就行

#include<stdio.h>
#include<string.h>
#include<iostream>
#include<algorithm>
using namespace std;
const  int maxn=100005;
int father[maxn];
int indegree[maxn];
int n,m;
int a[maxn];
void init(){
    for(int i=1;i<=n;i++)
        father[i]=i;
}
int find(int u){
   if(father[u]!=u)
    father[u]=find(father[u]);
   return father[u];
}
void Union(int x,int y){
     int t1=find(x);
     int t2=find(y);
     if(t1!=t2)
        father[t1]=t2;
}
int main(){
   while(scanf("%d%d",&n,&m)!=EOF){
        init();
      // memset(father,0,sizeof(father));
       memset(indegree,0,sizeof(indegree));
       memset(a,-1,sizeof(a));
       for(int i=1;i<=m;i++){
           int u,v;
          scanf("%d%d",&u,&v);
          indegree[u]++;
          indegree[v]++;
           Union(u,v);
       }

       for(int i=1;i<=n;i++){
           int t=find(i);
           if(a[t]==-1&&indegree[i]>0)
            a[t]=0;
           if(indegree[i]&1)
            a[t]++;
       }
int ans=0;
       for(int i=1;i<=n;i++){
        if(a[i]==0)
            ans++;
        else if(a[i]>0)
            ans+=a[i]/2;
       }
       printf("%d\n",ans);
   }
   return 0;
}

 

posted on 2020-05-25 09:03  zsben  阅读(104)  评论(0编辑  收藏  举报

导航