这是一篇十分正经的博客。
欧拉图
通过图(无向图或有向图)中所有边且每边仅通过一次通路称为欧拉通路,相应的回路称为欧拉回路。具有欧拉回路的图称为欧拉图(Euler Graph),具有欧拉通路而无欧拉回路的图称为半欧拉图。
相关定理
- 无向连通图G是欧拉图,当且仅当G不含奇数度结点(G的所有结点度数为偶数);
- 无向连通图G含有欧拉通路,当且仅当G有零个或两个奇数度的结点;
- 有向连通图D是欧拉图,当且仅当该图为连通图且D中每个结点的入度=出度
- 有向连通图D含有欧拉通路,当且仅当该图为连通图且D中除两个结点外,其余每个结点的入度=出度,且此两点满足deg-(u)-deg+(v)=±1。(起始点s的入度=出度-1,结束点t的出度=入度-1 或两个点的入度=出度)
- 一个非平凡连通图是欧拉图当且仅当它的每条边属于奇数个环。
- 如果图G是欧拉图且 H = G - uv,则H有奇数个u,v-迹仅在最后访问v;同时,在这一序列的u,v-迹中,不是路径的迹的条数是偶数。(Todia[1973])
一笔画
题目描述
一个图能否一笔画成,如果能请你每次都从当前最小编号的点开始画起,如果不行,则输出“no answer”
输入
4
0 1 0 0
1 0 1 1
0 1 0 1
0 1 1 0
输出
1 2 3 4 2
裸裸欧拉图!
1. 此题无向图
2. 并查集判断图示是否连通,不连通直接输出“no answer”
3. 判断图中入度为奇数得点有2个或0个;2个,一个为起点另一个为终点;0个,任何一个都可为起点。
4. dfs输出路径
1 #include<stdio.h> 2 3 int n,tot,b,e; 4 int f[1001],d[1001]; 5 int v[1001][1001],m[1001][1001]; 6 7 int get(int x){ 8 return x==f[x]?x : f[x]=get(f[x]); 9 } 10 11 void dfs(int x){ 12 printf("%d ",x); 13 for(int i=1;i<=n;i++){ 14 if(m[x][i]&&!v[x][i]){ 15 v[x][i]=1; 16 v[i][x]=1; 17 dfs(i); 18 } 19 } 20 } 21 22 int main(){ 23 scanf("%d",&n); 24 25 for(int i=1;i<=n;i++)f[i]=i; 26 for(int i=1;i<=n;i++){ 27 for(int j=1;j<=n;j++){ 28 scanf("%d",&m[i][j]); 29 if(m[i][j]==1){ 30 d[i]++; 31 int p=get(i); 32 int q=get(j); 33 if(p!=q){ 34 f[p]=f[q]; 35 tot++; 36 } 37 } 38 } 39 } 40 if(tot!=n-1){//判断图是否连通 41 printf("no answer"); 42 return 0; 43 } 44 for(int i=1;i<=n;i++){ 45 if(d[i]&1){//判断入度是否为奇数 46 if(b==0)b=i; 47 else if(e==0)e=i; 48 else {//入读为奇数点不是0或2 49 printf("no answer"); 50 return 0; 51 } 52 } 53 } 54 if(b!=0) dfs(b); 55 else dfs(1); 56 57 return 0; 58 }