accoders NOI #5011. 小j 的组合 题解
哈密顿回路需要把每个点经过且只经过一遍,而在树上,这只能是一条链。
手推一下可以发现,操作相当于把每个点复制一遍,等同于给允许这个点多经过一次,有了这个结论就容易了许多。
在树上 DFS,每次返回到父亲就操作一次,但这样不能保证操作最少(当然,最后不需要回到根节点)。
不需要返回的点构成了一条链,剩下的每个点都需要返回操作一次,那么显然当这条链最长也就是直径的时候,操作次数最少。
直接找出直径模拟即可。
// D. 小j 的组合
#pragma GCC optimize(2)
#include <bits/stdc++.h>
using namespace std;
int dis[105][105], n, num;
bool vis[105];
vector<int> ans;
namespace FASTIO {
inline int read() {
int res = 0, f = 1;
char ch = getchar();
while (!isdigit(ch)) {
if (ch == '-')
f = -1;
ch = getchar();
}
while (isdigit(ch)) {
res = res * 10 + ch - '0';
ch = getchar();
}
return res * f;
}
inline void write(int x) {
int top = 0;
char s[25];
do {
s[++top] = x % 10 + '0';
x /= 10;
} while (x);
while (top) putchar(s[top--]);
return;
}
} // namespace FASTIO
using namespace FASTIO;
namespace GRAPH {
inline void floyd() {
for (register int k = 1; k <= n; k++)
for (register int i = 1; i <= n; i++)
for (register int j = 1; j <= n; j++) dis[i][j] = min(dis[i][j], dis[j][k] + dis[i][k]);
return;
}
void DFS(const int &k, const int &t) {
int v = 0;
ans.emplace_back(k);
vis[k] = true;
for (register int i = 1; i <= n; i++) {
if (!vis[i] && dis[k][i] == 1) {
if (dis[t][k] == dis[t][i] + 1) {
v = i;
continue;
}
DFS(i, t);
write(k);
putchar(' ');
ans.emplace_back(++num);
}
}
if (v)
DFS(v, t);
return;
}
} // namespace GRAPH
using namespace GRAPH;
int main() {
freopen("combo.in", "r", stdin);
freopen("combo.out", "w", stdout);
int u, v, s, t;
n = read();
for (register int i = 1; i <= n; i++) {
for (register int j = 1; j <= n; j++) {
if (i == j)
dis[i][j] = 0;
else
dis[i][j] = 114514;
}
}
for (register int i = 1; i < n; i++) {
u = read();
v = read();
dis[u][v] = dis[v][u] = 1;
}
floyd();
s = t = 1;
for (register int i = 1; i <= n; i++) {
for (register int j = 1; j <= n; j++) {
if (dis[i][j] > dis[s][t]) {
s = i;
t = j;
}
}
}
/*cout<<"fuck\n";
exit(0);*/
write(n - dis[s][t] - 1);
putchar('\n');
num = n;
DFS(s, t);
putchar('\n');
for (int u : ans) {
write(u);
putchar(' ');
}
putchar('\n');
fclose(stdin);
fclose(stdout);
return 0;
}
/*
* accoders NOI-2022NOIP A层联测11
* http://47.92.197.167:5283/contest/266/problem/4
* -DONLINE_JUDGE -O2 -std=c++11
* 2022.10.18
*/

浙公网安备 33010602011771号