Codeforces Round #633 (Div. 2) D. Edge Weight Assignment 思维or猜猜猜

https://codeforces.ml/contest/1339/problem/D

给定一个n个顶点的未加权的树,现在你要给每条边分配一个正权重,满足条件:树中每两个不同叶子节点之间的简单路径所有边权按位XOR值为0。

可以放很大(无限大)的数,例如:10(1010),,,

可以确保此类分配在给定约束条件下存在。

定义 f 为叶子节点之间的简单路径上不同边权的数量。

求 f 的最小值和最大值。

例如:

例1.

 第一棵树叶子节点1 -> 6之间不同的边权数量为1 (1),所有f=1。

 第二棵树叶子节点1 -> 6之间不同的边权数量为4 (1,2,4,7),所有f=4。

f 最小值为1,最大值为4.

例2.

f 最小值最大值都为3.

 思路:首先思考最小值,偶数个相同的数异或为0,那么当俩叶子节点之间的边数为偶数时边权都相同就可以了,所以 f最小值为1;当边数出现奇数时,三个相同的数异或值肯定不为0,两个相同的数和一个不同的数异或也肯定不为0,那么就至少要三个不同的数异或,比如边数为5:那么就两个相同的数异或为0,三个不同的数来异或,使异或值为0,如:1^1^1^2^3.所以当边数为奇数时f最小值为3(不可能出现边数为1)。

思考最大值:边数为2的话,这俩数肯定相等,边数不为2的情况,f 就等于边数(我也不知道为什么,猜猜猜,虽然树可能会长的很复杂很奇葩,但应该总能找到那么几个数异或等于0???题目特别说了权重可以非常大,hhhhhh,,,如果有大佬能证明的话,求告知)。

总结:最小值只需要判断叶子节点之间的边数是否有奇数条就可以了,全偶数为1,有奇数为3;

最大值只需找出边数为2的叶子节点,然后减去,先把 f 设为总边数(n-1),同一个根节点连的叶子节点的数量为sum,那么 f=f-(sum-1)(sum≥2).

#include <bits/stdc++.h>
using namespace std;
const int MAXN=4e5+5;
const int mod=1e9+7;
typedef long long ll;
//typedef __int128 LL;
const int inf=0x3f3f3f3f;
const long long INF=0x3f3f3f3f3f3f3f3f;
vector<int>g[MAXN];
int vis[MAXN];
int len=0;//树的深度,只要顶点到叶子的距离有为奇数的,那么俩叶子节点的边数肯定有为奇数的,同样,如果全为偶数,肯定不存在边数为奇数,就不用计算每两个叶子节点的距离了
int ansmax,ansmin=1;
void dfs(int u)
{
    int sum=0;//同根的叶子节点个数
    for(int i=0;i<g[u].size();i++)
    {
        int v=g[u][i];
        if(vis[v]==1)continue;
        len++;
        vis[v]=1;
        if(g[v].size()==1)
        {
            sum++;
            if(len%2&&len>=3)ansmin=3;
        }
        dfs(v);
        len--;
    }
    if(sum>=2||len==1)
    {
        if(len==1)ansmax=ansmax-sum;
        else ansmax=ansmax-sum+1;
    }
}
int main()
{
    int n;
    scanf("%d",&n);
    int u,v;
    for(int i=1;i<=n-1;i++)
    {
        v,u;
        scanf("%d%d",&v,&u);
        g[v].push_back(u);
        g[u].push_back(v);
    }
    for(int i=1;i<=n;i++)
    {
        if(g[i].size()==1)
        {
            u=i;//以叶子节点作为顶点
            break;
        }
    }
    ansmax=n-1;
    vis[u]=1;
    dfs(u);
    printf("%d %d\n",ansmin,ansmax);
    return 0;
}
View Code

猜你喜欢

转载自www.cnblogs.com/MZRONG/p/12690971.html