码迷,mamicode.com
首页 > 其他好文 > 详细

poj2942 Knights of the Round Table

时间:2019-10-31 00:39:52      阅读:72      评论:0      收藏:0      [点我收藏+]

标签:string   lse   struct   pre   判断   ipa   iostream   刘汝佳   开始   

好久之前就注册了一直没写 今天开始把刷的题都放在上面

这个题就是建个补图找双连通分量然后染色判断是不是二分图(奇圈一定不是二分图)

re了好多次 debug2小时 最后发现栈数组开小了。。。

#include<iostream>
#include<cstring>
#include<cstdio>
#include<algorithm>
#include<vector>
using namespace std;
const int maxn=1010;
struct Edge
{
    int u,v;
}s[1000010];
int dfn[maxn],low[maxn],cnt=0,cnt_bcc=0,a[maxn][maxn],N,M,Index=0,belong[maxn],col[maxn];
bool iscut[maxn],mk[maxn];
vector<int> edges[maxn];
vector<int> bcc[maxn];
void addedge(int u,int v)
{
    edges[u].push_back(v);
    edges[v].push_back(u);
}
bool isbipartite(int u,int C)
{
    for(int i=0;i<edges[u].size();i++)
    {
        int v=edges[u][i];
        if(belong[v]!=C) continue;
        if(col[u]==col[v]) return false;
        if(!col[v])
        {    
            col[v]=3-col[u];
            if(!isbipartite(v,C)) return false;
//            return isbipartite(v,C);
        }
    }
    return true;
}
void init()
{
    for(int i=1;i<=N;i++)
        edges[i].clear();
    memset(a,0,sizeof a);
    memset(dfn,0,sizeof dfn);
    memset(belong,0,sizeof belong);
    memset(iscut,false,sizeof iscut);
    memset(mk,false,sizeof mk);
    cnt=0;cnt_bcc=0;
}
void tarjan(int u,int fa)
{
    int child=0;
    dfn[u]=low[u]=++cnt;
    for(int i=0;i<edges[u].size();i++)
    {
        int v=edges[u][i];
        if(!dfn[v])
        {
            child++;
            s[++Index]=(Edge){u,v};
            tarjan(v,u);
            low[u]=min(low[u],low[v]);
            if(low[v]>=dfn[u])
            {
                iscut[u]=true;cnt_bcc++;
                bcc[cnt_bcc].clear();
                for(Edge e;;)
                {
                    e=s[Index--];
                    if(belong[e.u]!=cnt_bcc){belong[e.u]=cnt_bcc;bcc[cnt_bcc].push_back(e.u);}
                    if(belong[e.v]!=cnt_bcc){belong[e.v]=cnt_bcc;bcc[cnt_bcc].push_back(e.v);}
                    if(e.u==u&&e.v==v) break;
                }
            }
        }
        else if(dfn[v]<dfn[u]&&fa!=v)
        {
            s[++Index]=(Edge){u,v};
            low[u]=min(low[u],dfn[v]);
        }
        if(child==1&&fa==0) iscut[u]=false;
    }
}
int main()
{
    while(true)
    {

        scanf("%d%d",&N,&M);
        if(N==0&&M==0) break;
        init();
        for(int i=1;i<=M;i++)
        {
            int u,v;
            scanf("%d%d",&u,&v);
            a[u][v]=1;a[v][u]=1;
        }
        for(int i=1;i<=N;i++)
            for(int j=1+i;j<=N;j++)
                if(!a[i][j]) addedge(i,j);
        for(int i=1;i<=N;i++)
            if(!dfn[i]) tarjan(i,0);
        for(int i=1;i<=cnt_bcc;i++)
        {
            memset(col,0,sizeof col);
            for(int j=0;j<bcc[i].size();j++)
                belong[bcc[i][j]]=i;
            col[bcc[i][0]]=1;
            if(!isbipartite(bcc[i][0],i))
                for(int j=0;j<bcc[i].size();j++)
                    mk[bcc[i][j]]=1;
        }
        int ans=N;
        for(int i=1;i<=N;i++)
            if(mk[i]) ans--;
        printf("%d\n",ans);
    }
    return 0;
}

看的蓝书的思路 debug时把代码刘汝佳化了

poj2942 Knights of the Round Table

标签:string   lse   struct   pre   判断   ipa   iostream   刘汝佳   开始   

原文地址:https://www.cnblogs.com/tmzengbi/p/11768681.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!