Luogu P3237 [HNOI2014]米特运输 题解

2022-09-19 11:35:46 浏览数 (1)

Luogu P3237 [HNOI2014]米特运输 题解

Description

题目链接

又臭又长的题面差评

给定一棵树,该树满足一定的性质:

  1. 节点 x 的所有子节点权值必须相等
  2. 节点 x 的所有子节点的权值之和等于 x 的权值

Solution

设第 x 个节点的权值为 v,它有 sz[x] 个直系子节点,显然,这 sz[x] 个直系子节点的权值均为 frac{v}{sz[x]}

考虑设 f[i] 表示第 i 个节点不修改时的根节点的权值。

显然可得根节点的权值为:

v[i] times prod sz[x] (x in {fa}_v)

那么只要计算出 1nf[i],判断相等个数即可。

由于乘法可能会爆 long long,所以开个 mapmod 一下。

Code

代码语言:javascript复制
#include<cstdio>
#include<vector>
#include<map>
#define LL long long
#define max(x,y) ((x)>(y)?(x):(y))
#define W while
#define I inline
#define ig(c) ('0'<=(c)&&(c)<='9')
#define gc getchar
I int read(){int x=0,f=1;char c=gc();W(!ig(c)) f=c=='-'?-1:f,c=gc();W(ig(c)) x=(x<<3) (x<<1) (c&15),c=gc();return x*f;}
I void write(int x){x<0&&(putchar('-'),x=-x,0),x<10?(putchar(x '0'),0):(write(x/10),putchar(x '0'),0);}
const int N=500010,mod=19260817;
int n,a[N],f[N],ans;
std::vector<int> v[N];
std::map<int,int> mp;
I void dfs(int x,int fa,int sum){
int s=0;for(auto i:v[x]) (i^fa)&&(s  ,0);
  mp[(int)(1ll*sum*a[x]%mod)];
ans=max(ans,mp[(int)(1ll*sum*a[x]%mod)]);
sum=1ll*sum*s%mod;
for(auto i:v[x]) (i^fa)&&(dfs(i,x,sum),0);
}
int main(){
n=read();for(int i=1;i<=n;i  ) a[i]=read();
for(int x,y,i=1;i<n;i  ) x=read(),y=read(),v[x].push_back(y),v[y].push_back(x);
mp.clear();dfs(1,0,1ll);
return write(n-ans),0;
}

0 人点赞