bzoj 2152:聪聪可可(点分治)
来源:互联网 发布:淘宝转盘抽奖怎么做 编辑:程序博客网 时间:2024/05/21 22:42
题面
题意:给你一棵树,有边权。随机选两个点,问它们路径长度为3的倍数的概率。
直接考虑点分治,还是找到重心x。用一遍dfs找出当前连通块内,到x距离模3为0,1,2的点分别有几个,然后统计答案。同一个连通块的点的路径不经过x,是不合法的,减去即可。
#include <iostream>#include <fstream>#include <algorithm>#include <cmath>#include <ctime>#include <cstdio>#include <cstdlib>#include <cstring>using namespace std;#define mmst(a, b) memset(a, b, sizeof(a))#define mmcp(a, b) memcpy(a, b, sizeof(b))typedef long long LL;const int N=40040,oo=1e9+7;void read(int &hy){ hy=0; char cc=getchar(); while(cc<'0'||cc>'9') cc=getchar(); while(cc>='0'&&cc<='9') { hy=(hy<<3)+(hy<<1)+cc-'0'; cc=getchar(); }}int n;int to[N],nex[N],val[N],head[N],cnt;int pre[N],siz[N],d[N],vis[N],root,sum;int dep[N],a[N];int ans,by[3];void add(int u,int v,int w){ to[++cnt]=v; val[cnt]=w; nex[cnt]=head[u]; head[u]=cnt;}void dfsRoot(int x,int fa){ pre[x]=fa; siz[x]=1; d[x]=0; for(int h=head[x];h;h=nex[h]) if(!vis[to[h]]&&to[h]!=fa) { dfsRoot(to[h],x); siz[x]+=siz[to[h]]; d[x]=max(d[x],siz[to[h]]); } d[x]=max(d[x],sum-siz[x]); if(d[x]<d[root]) root=x;}void dfsDeep(int x,int fa){ a[++a[0]]=dep[x]; for(int h=head[x];h;h=nex[h]) if(!vis[to[h]]&&to[h]!=fa) { dep[to[h]]=(dep[x]+val[h])%3; dfsDeep(to[h],x); }}int cal(int x,int now){ dep[x]=now; a[0]=0; dfsDeep(x,0); by[0]=by[1]=by[2]=0; for(int i=1;i<=a[0];i++) by[a[i]]++; return by[0]*by[0]+by[1]*by[2]*2;}void dfsSol(int x){ siz[pre[x]]=sum-siz[x]; vis[x]=1; ans+=cal(x,0); for(int h=head[x];h;h=nex[h]) if(!vis[to[h]]) { ans-=cal(to[h],val[h]); sum=siz[to[h]]; root=0; dfsRoot(to[h],0); dfsSol(root); }}int gcd(int x,int y){ if(!y) return x; return gcd(y,x%y);}int main(){ cin>>n; ans=0; for(int i=1;i<=n-1;i++) { int u,v,w; read(u); read(v); read(w); w=w%3; add(u,v,w); add(v,u,w); } sum=n; root=0; d[0]=oo; dfsRoot(1,0); dfsSol(root); int gc=gcd(ans,n*n); int fenmu=n*n/gc,fenzi=ans/gc; cout<<fenzi<<"/"<<fenmu<<endl;}
阅读全文
0 0
- 【BZOJ】2152: 聪聪可可 点分治
- bzoj 2152: 聪聪可可 点分治
- 【BZOJ 2152】聪聪可可 点分治
- Bzoj 2152: 聪聪可可(点分治)
- BZOJ 2152: 聪聪可可 点分治
- 【BZOJ】2152 聪聪可可 点分治
- BZOJ 2152: 聪聪可可 点分治
- bzoj 2152 聪聪可可(点分治)
- bzoj 2152: 聪聪可可(点分治)
- bzoj 2152:聪聪可可(点分治)
- bzoj 2152: 聪聪可可(树的点分治)
- 【bzoj 2152】聪聪可可(树的点分治)
- BZOJ 2152 聪聪可可 树的点分治
- BZOJ 2152 聪聪可可 (树上点分治)
- BZOJ 2152: 聪聪可可 点分治/树dp
- [bzoj 2152] 聪聪可可 树上点分治
- BZOJ 2152: 聪聪可可(点分治/树形DP)
- 【BZOJ 2152 聪聪可可】【点分治 + 一个套路】
- 使用ICON动态修改exe文件图标
- C++/CLI 创建WPF程序
- 数据结构——栈—出栈顺序的可能情况
- 面试题
- 喜迎国庆,欢度中秋,联科教育送大礼!
- bzoj 2152:聪聪可可(点分治)
- 免费馅饼 dp
- bzoj3206 [Apio2013]道路费用(kruskal+并查集+状压枚举+dfs)
- TCP的三次握手
- 心脏出血漏洞修复记录
- centos 更改源
- vmware fusion 10序列号
- 内存(一)
- 使用JavaSocket编写发送TCP请求的工具类