弦图的判定MCS算法(zoj1015)

来源:互联网 发布:淘宝买产品送刀具骗法 编辑:程序博客网 时间:2024/04/29 18:27

题意:裸的弦图的判定:

弦图定义:给出一个无向连通图,如果每个环中都存在至少一条弦(环中存在不相邻的两点直接相连)这样的图叫做弦图;

转载:http://blog.csdn.net/crux_d/article/details/2251963

以下是时间复杂度为O(n+m)的算法,n是图的点数,m是图的边数。 
第一步:给节点编号 
设已编号的节点集合为A,未编号的节点集合为B 
开始时A为空,B包含所有节点。 
for num=n-1 downto 0 do 

在B中找节点x,使与x相邻的在A集合中的节点数最多,将x编号为num, 
并从B移入A 

第二步:检查 
for num=0 to n-1 do 

对编号为num的节点x,设所有编号大于num且与x相邻的节点集合为C, 
在集合C中找出编号最小的节点y,如果集合C中存在不等于y的节点z, 
且y与z间没有边,则此图不是弦图,退出。 

检查完了,则此图是弦图。 

原始算法:

#include"stdio.h"#include"string.h"#include"stdlib.h"#include"queue"#include"algorithm"#include"string.h"#include"string"#include"math.h"#include"vector"#include"stack"#include"map"#define eps 1e-4#define inf 0x3f3f3f3f#define M 1209#define PI acos(-1.0)using namespace std;int cnt,vis[M],num[M],s[M],g[M][M];void bfs(int n){    int i,j,id;    memset(vis,0,sizeof(vis));    memset(num,0,sizeof(num));    cnt=0;    for(i=n;i>=1;i--)    {        id=1;        for(j=1;j<=n;j++)        {            if(!vis[j]&&num[id]<num[j])            {                id=j;            }        }        s[i]=id;        vis[id]=1;        for(j=1;j<=n;j++)        {            if(id!=j&&g[id][j]&&!vis[j])                num[j]++;        }    }}int psq(int n){    int i,j;    for(i=1;i<=n;i++)    {        int id;        for(j=i+1;j<=n;j++)        {            if(g[s[i]][s[j]])            {                id=j;                break;            }        }        for(j=i+1;j<=n;j++)        {            if(g[s[i]][s[j]]&&id!=j&&g[s[id]][s[j]]==0)            return 0;        }    }    return 1;}int main(){    int n,m,i;    while(scanf("%d%d",&n,&m),m+n)    {        memset(g,0,sizeof(g));        for(i=0;i<m;i++)        {            int a,b;            scanf("%d%d",&a,&b);            g[a][b]=g[b][a]=1;        }        bfs(n);        if(psq(n))        {            printf("Perfect\n\n");        }        else            printf("Imperfect\n\n");    }    return 0;}
bfs+优先队列

#include"stdio.h"#include"string.h"#include"stdlib.h"#include"queue"#include"algorithm"#include"string.h"#include"string"#include"math.h"#include"vector"#include"stack"#include"map"#define eps 1e-4#define inf 0x3f3f3f3f#define M 1009#define PI acos(-1.0)using namespace std;struct Edge{    int v;    Edge(int vv)    {        v=vv;    }};vector<Edge>edge[M];struct node{    int id,num;    friend bool operator<(node a,node b)    {        return a.num<b.num;    }};int n,num[M],vis[M],link[M],cnt,order[M],q[M],g[M][M];void bfs(int u){    priority_queue<node>q;    memset(num,0,sizeof(num));    memset(link,0,sizeof(link));    memset(vis,0,sizeof(vis));    cnt=n;    node now;    now.id=u;    now.num=1;    q.push(now);    while(!q.empty())    {        node cur=q.top();        if(!vis[cur.id])        {            vis[cur.id]=1;            link[cnt]=cur.id;            order[cur.id]=cnt;            cnt--;            if(cnt==0)                break;        }        q.pop();        for(int i=0;i<(int)edge[cur.id].size();i++)        {            int v=edge[cur.id][i].v;            num[v]++;            now.id=v;            now.num=num[v];            if(!vis[v])                q.push(now);        }    }}int check(){    int i,j,value;    bfs(1);    for(i=1;i<=n;i++)    {        int mini=n+1;        int t=0;        for(j=0;j<(int)edge[link[i]].size();j++)        {            int v=edge[link[i]][j].v;            if(order[v]>i)            {                if(mini>order[v])                {                    mini=order[v];                    value=v;                }                q[t++]=v;            }        }        for(j=0;j<t;j++)        {            if(q[j]!=value&&g[value][q[j]]==0)                return 0;        }    }    return 1;}int main(){    int m,i,a,b;    while(scanf("%d%d",&n,&m),m||n)    {        for(i=1;i<=n;i++)            edge[i].clear();        memset(g,0,sizeof(g));        for(i=0;i<m;i++)        {            scanf("%d%d",&a,&b);            edge[a].push_back(b);            edge[b].push_back(a);            g[a][b]=g[b][a]=1;        }        if(check())            printf("Perfect\n\n");        else            printf("Imperfect\n\n");    }}



0 0
原创粉丝点击