欧拉路

欧拉路:
如果给定无孤立结点图G,若存在一条路,经过图中每边一次且仅一次,这条路称为欧拉路;
如果给定无孤立结点图G,若存在一条回路,经过图中每边一次且仅一次,那么该回路称为欧拉回路。
存在欧拉回路的图,称为欧拉图。

一、 对于无向图G,具有一条欧拉路,当且仅当G是连通的,且有零个或两个奇数度结点。
且有零个奇数度结点,存在欧拉回路;有两个奇数度结点,存在欧拉路。

判断无向图G是否连通,可以从任意结点出发,进行深度优先遍历,如果可以遍历到所有点,也可以用并查集,判断根节点的个数,
说明,图G连通,否则,图G不连通。

http://acm.nyist.net/JudgeOnline/problem.php?pid=42

 
#include<stdio.h>
#include<string.h>
int pre[1001];
int dds[1001];
void init(int n)
{
	int i;
	for(i=1;i<=n;i++)
		pre[i]=i;
}
int find(int x)
{
	if(x!=pre[x])
		pre[x]=find(pre[x]);
	return pre[x];
}
void uunion(int x,int y)
{
	x=find(x);
	y=find(y);
	if(x!=y)
	 pre[y]=x;
}
int main()
{
	int i,j,k,cc,n,m;
	int start, end;  
    
	scanf("%d",&cc);
	while(cc--)
	{  memset(dds,0,sizeof(dds));
		scanf("%d%d",&n,&m);
		init(n);
		for(i=1;i<=m;i++)
		{
			scanf("%d%d",&start,&end);
			uunion(start,end);
			dds[start]=!dds[start];//只记录奇偶性,1为奇度,0为偶度  
            dds[end]=!dds[end]; 
		}
		int sum_root=0,sum_ji=0;//根结点的个数,记录奇度顶点个数
		for(i=1;i<=n;i++)
		{	if(pre[i]==i) sum_root++;
			if(dds[i]) sum_ji++;
		}
		if(sum_root>1)
		{	printf("No\n"); continue;}
		if(sum_ji==0||sum_ji==2)
			printf("Yes\n");
		else
			printf("No\n");
	}
	return 0;
}


        

http://acm.nyist.net/JudgeOnline/problem.php?pid=230 彩色棒

 
#include<stdio.h>
#include<string.h>
#include<stdlib.h>
#define maxn 500002
typedef struct node
{
    int order;  //编号。
    struct node *next[26];
}node;
int pre[maxn];
int vs[maxn];
int t;
int search(char *s,node *T)
{
    int len,i,j,id,flag=0;
    node *p,*q;
    len=strlen(s);
    p=T;
    for(i=0;i<len;++i)
    {
        id=s[i]-'a';
        if(p->next[id]==NULL)
        {
            flag=1;
            q=(node *)malloc(sizeof(node));
            for(j=0;j<26;++j)
                q->next[j]=NULL;
            p->next[id]=q;
        }
        p=p->next[id];
     }
     if(flag)  //颜色不存在。
     {
         p->order=t++;
         vs[p->order]=!vs[p->order];
         return p->order;
     }
     else
     {
        vs[p->order]=!vs[p->order];
        return p->order;
     }
}
int find(int x)
{
    if(pre[x]==-1) return x;
    return pre[x]=find(pre[x]);
}
void Union(int x,int y)
{
     x=find(x);
     y=find(y);
     if(x!=y)
      pre[y]=x;
}
int main()
{
     //freopen("Input.txt","r",stdin);
     int i,num1,num2,ncase,n;
     char s1[20],s2[20];
     node *T;
     scanf("%d",&ncase);
     while(ncase--)
     {
         t=1;
         memset(vs,0,sizeof(vs));
         memset(pre,-1,sizeof(pre));
         T=(node *)malloc(sizeof(node));
         T->order=0;
         for(i=0;i<26;++i)
           T->next[i]=NULL;
         scanf("%d",&n);
         if(n==0) { printf("Possible\n"); continue ;}
         for(i=1;i<=n;i++)
         {
            scanf("%s%s",s1,s2);
            num1=search(s1,T);
            num2=search(s2,T);
            Union(num1,num2);
         }
         int ans=0,sum=0;
         for(i=1;i<t;i++)
         {
             if(pre[i]==-1) ans++;
             if(vs[i]) sum++;
         }
         if(ans>1)  printf("Impossible\n");
         else
         {
             if(sum==2||sum==0)
                printf("Possible\n");
             else
                printf("Impossible\n");
         }
     }
    return 0;
}
        


二 、对于有向图G,具有一条单向欧拉路,当且仅当G是连通的,且每个结点入度等于出度,或者,

除两个结点外,每个结点的入度等于出度,而这两个结点满足,一个结点的入度比出度大1,
另一个结点的入度比出度小1。

判断有向图G是否连通,可以某一结点出发,进行深度优先遍历,如果存在一点作为初始结点
可以遍历到所有点,说明,图G连通,否则,图G不连通。



评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值