树上博弈

树上博弈

http://www.nowcoder.com/questionTerminal/28d84dec511242fda315ca0223476aac

树上博弈
https://ac.nowcoder.com/acm/contest/3005/F
图片说明
图片说明
首先,注意到输掉的唯一方法是自己的唯一一条边有另一个人,那么自己一定是在叶子上。
令两个人之间的距离为D。请注意,每人行动后D增加1或减少1。 因此,每有人走一步D的奇偶性都会改变。
假设最初,在牛牛移动之前,D是偶数。 那么当牛牛移动时D将始终为偶数,而当牛妹移动时D将始终为奇数。
请注意,只要牛牛和牛妹的令牌位于相邻的节点中,D=1。因此,如果D为偶数,则他们不在相邻的单元格中,并且牛牛始终可以移动。
另一方面,由于牛牛总是可以移动,因此他可以向牛妹的方向移动,将牛妹必然会最终移动到叶子上。同样,如果最初D是奇数,则牛妹获胜。
因此,答案取决于距离的奇偶性:如果是偶数,则牛牛获胜,否则牛妹获胜。
可以发现,只有牛牛的初始位置和牛妹的初始位置距离为偶数时,牛牛获胜。只需要分别求出深度为奇数的点和深度为偶数的点的数量即可。
cnt 为 ll

#pragma warning (disable :4996)
#include <iostream>
#include <cstdio>
#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
const ll mod = 1e9 + 7;
const int N = 1e6 + 10;

int n;
int Depth[N];
ll cnt[2];
int main() {
    scanf("%d", &n);
    Depth[1] = 0;
    cnt[0] = 1;
    for (int i = 2; i <= n; i++) {
        int c;
        scanf("%d", &c);

        Depth[i] = Depth[c] + 1;
        cnt[Depth[i] & 1]++;
    }
    cout << cnt[0] * (cnt[0] - 1) + cnt[1] * (cnt[1] - 1) << endl;
}
全部评论

相关推荐

和光同尘cc:给我发就算了,还敢恶心上交✌🏻
点赞 评论 收藏
分享
点赞 收藏 评论
分享
牛客网
牛客企业服务