P2731 [USACO3.3]骑马修栅栏 Riding the Fences 欧拉回路 缩索
题目链接
首先要想每个边都走一次, 必须是所有点都是偶点或者只有两个奇点.
然后我们找到那个编号最小的奇点或偶点开始走, 贪心的选取下一条边, 直到不能走为止.
注意统计路径的时候必须倒着统计, 正着统计会出大问题.比如样例:
(5 1 2 2 3 2 4 2 5 4 5).倒着统计答案应该是3 2 5 4 2 1, 而正着统计就会变成1 2 3 4 5 2
#include <bits/stdc++.h>
using namespace std;
inline long long read() {
long long s = 0, f = 1; char ch;
while(!isdigit(ch = getchar())) (ch == '-') && (f = -f);
for(s = ch ^ 48;isdigit(ch = getchar()); s = (s << 1) + (s << 3) + (ch ^ 48));
return s * f;
}
const int N = 1025;
int m, s, cnt, a[N][N], deg[N], road[N * 10];
int find(int x) {
for(int i = 1;i < N; i++) if(a[x][i]) { a[x][i] --; a[i][x] --; find(i); }
road[++ cnt] = x;
}
int main() {
m = read();
for(int i = 1, x, y;i <= m; i++)
x = read(), y = read(), a[x][y] ++, a[y][x] ++, deg[x] ++, deg[y] ++;
s = 1;
for(int i = 1;i < N; i++) if(deg[i] & 1) { s = i; break; }
find(s);
for(int i = cnt;i >= 1; i--) printf("%d
", road[i]);
return 0;
}