题目链接:点击打开链接
思路:按照题目给出的定理判断即可,同时该定理比较重要,要熟记。
#include <cstdio>
#include <cstring>
#include <iostream>
#include <queue>
using namespace std;
int degree[505];
int cnt,head[505];
int u[250010],v[250010],nex[250010];
void add(int x,int y){
cnt++;
u[cnt] = x;
v[cnt] = y;
nex[cnt] = head[x];
head[x] = cnt;
}
int bfs(int x,int n){//判断连不连通
int book[505];
queue<int> q;
q.push(x);
memset(book,0,sizeof(book));
book[x] = 1;
while(!q.empty()){
int t = q.front();
q.pop();
for(int i = head[t];i;i = nex[i]){
if(book[v[i]]) continue;
book[v[i]] = 1;
q.push(v[i]);
}
}
for(int i = 1;i <= n;i++){
if(!book[i]) return 0;
}
return 1;
}
int calDegree(int n){//计算奇度顶点的个数
int cnt = 0;
for(int i = 1;i <= n;i++){
if(degree[i] % 2){
cnt++;
}
}
return cnt;
}
int main(){
int n,m;
int x,y;
scanf("%d%d",&n,&m);
cnt = 0;
memset(degree,0,sizeof(degree));
memset(head,0,sizeof(head));
memset(nex,0,sizeof(nex));
for(int i = 1;i <= m;i++){
scanf("%d%d",&x,&y);
degree[x]++;
degree[y]++;
add(x,y);
add(y,x);
}
int flag1 = bfs(1,n);
int num = calDegree(n);
for(int i = 1;i <= n;i++){
printf("%d%c",degree[i],i == n ? '\n':' ');
}
if(flag1 && num == 0){//连通图,顶点度数均为偶数
printf("Eulerian");
}
else if(flag1 && num == 2){//连通图,两个顶点度数为奇数
printf("Semi-Eulerian");
}
else{
puts("Non-Eulerian");
}
return 0;
}