社区讨论
此处悬赏 5RMB 求调(必须是楼主的思路)
P2279[HNOI2003] 消防局的设立参与者 5已保存回复 16
讨论操作
快速查看讨论及其快照的属性,并进行相关操作。
- 当前回复
- 16 条
- 当前快照
- 1 份
- 快照标识符
- @mlgxv8qu
- 此快照首次捕获于
- 2026/02/11 02:33 上周
- 此快照最后确认于
- 2026/02/11 02:39 上周
WA50pts,评测。
当然证明楼主的思路不可能 AC(完全错误)也可以。
真的通过可以加楼主微信,id 为 lyh_17772458533。
CPP#include<bits/stdc++.h>
using namespace std;
const int N = 1e4 + 5;
int n, root;
vector<int> graph[N];
int ans;
int rnd[N];//层数
int fa[N];
bool pull[N];//是否覆盖
void dfs(int u, int father)
{
if (graph[u].size() == 1 && graph[u][0] == father)
{
rnd[u] = 1;
return;
}
bool flag_deal = 0;//剪枝优化
if (pull[u]) flag_deal = 1;
for (auto v : graph[u])
{
if (v == father) continue;
fa[v] = u;
dfs(v, u);
rnd[u] = max(rnd[v], rnd[u]);//取层数最大
}
rnd[u] += 1;
//如果儿子都已经处理,此点处于下一个范围中,层数为1
bool flag = 1;
for (auto it : graph[u])
{
if (it == father) continue;
flag = flag && pull[it];
}
if (flag)
{
rnd[u] = 1;
return;
}
//如果层数为3,此时利益最大化,处理覆盖
if (flag_deal == 0 &&rnd[u] == 3)
{
pull[u] = 1;
for (auto it : graph[u])
{
pull[it] = 1;
for (auto v : graph[it])
{
pull[v] = 1;
}
}
ans++;
}
}
int main()
{
ios::sync_with_stdio(false);
cin.tie(nullptr);
cout.tie(nullptr);
cin >> n;
root = 1;
for (int i = 2; i <= n; i++)
{
int j;
cin >> j;
graph[i].push_back(j);
graph[j].push_back(i);
}
// for (int i = 1; i < n; i++)
// {
// int u, v;
// cin >> u >> v;
// graph[u].push_back(v);
// graph[v].push_back(u);
// }
dfs(root, 0);
//处理层数不足3的范围
for (int i = 1; i <= n; i++)
{
if (pull[i] == 0)
{
ans++;
if (fa[i] != 0) i = fa[i];
pull[i] = 1;
for (auto it : graph[i])
{
pull[it] = 1;
for (auto j : graph[it])
{
pull[j] = 1;
}
}
}
}
cout << ans << "\n";
return 0;
}
/*
11
1 2 3 4 5 6 7 8 9 10
*/
回复
共 16 条回复,欢迎继续交流。
正在加载回复...