HDU 5468 Puzzled Elena(DFS序+容斥原理)
来源:互联网 发布:闲鱼淘宝小二介入 编辑:程序博客网 时间:2024/05/12 23:49
题目链接:传送门
题意:
给定一棵树,求这个节点的所有子树中包括他本身与它互质的节点的个数。
分析:转自传送门
因为每个数的大小<=100000 这个范围内 2*3*5*7*11*13 *17> 100000 最多只有 6 个素因子。
当我们知道这个怎么处理以后,我们可以利用dfs序,解决这个问题
我们求当前这个节点的答案时,用容斥搞就是:以这个节点为根的树的大小 - 有1个素因子和他相同的节点个数 + 有2个素因子和他相同的个数 - 有3个素因子和他相同的个数 ....
那么问题来了,我们如何求出有多少个 有1个素因子和他相同的个数,有2个素因子和他相同的个数 ,,,,,
我们维护一个数fac[]数组,fac[i] 代表包含因子i的节点个数。
那么在这颗树中,进入这颗树之前求一下(有1个素因子和他相同的节点个数,有2个素因子和他相同的节点个数.....),离开这颗树的时候再求一下(有1个素因子和他相同的节点个数,有2个素因子和他相同的节点个数.....),他们的差便是我们需要的(子树中的和他有关系的信息)。
到这里,问题就解决了,容斥版的做法 时间复杂度 O(n*2^6 + nlogn) :
代码如下:
#include <bits/stdc++.h>using namespace std;const int maxn = 1e5+10;int fac[maxn];int w[maxn];int ans[maxn];struct Graph{ vector<int >vc[maxn]; void init(){ for(int i=0;i<maxn;i++) vc[i].clear(); } void add(int u,int v){ vc[u].push_back(v); }}G1,G2;void prepare(){ G1.init(); for(int i=2;i<maxn;i++){ if(G1.vc[i].size()) continue; for(int j=i;j<maxn;j+=i) G1.add(j,i); }}int calc(int u,int x){ int ans = 0,n=G1.vc[u].size(); for(int i=1;i<(1<<n);i++){ int tot=1,cnt=0; for(int j=0;j<n;j++){ if((1<<j)&i){ cnt++; tot=tot*G1.vc[u][j]; } } if(cnt&1) ans = ans+fac[tot]; else ans = ans-fac[tot]; fac[tot]+=x; } return ans;}int dfs(int u,int pre){ int cnt = 0; int L = calc(w[u],0); for(int i=0;i<G2.vc[u].size();i++){ int v = G2.vc[u][i]; if(v==pre) continue; cnt+=dfs(v,u); } int R = calc(w[u],1); ans[u]=cnt-(R-L); if(w[u]==1) ans[u]++; return cnt+1;}int main(){ prepare(); int n,cas=1; while(~scanf("%d",&n)){ G2.init(); memset(fac,0,sizeof(fac)); int u,v; for(int i=1;i<n;i++){ scanf("%d%d",&u,&v); G2.add(u,v); G2.add(v,u); } for(int i=1;i<=n;i++) scanf("%d",w+i); dfs(1,0); printf("Case #%d: ",cas++); for(int i=1;i<=n;i++){ printf("%d%c",ans[i],i==n? '\n':' '); } } return 0;}
1 0
- HDU 5468 Puzzled Elena(DFS序+容斥原理)
- HDU 5468 Puzzled Elena(容斥原理+dfs)
- hdu 5468 Puzzled Elena(前缀性质+dfs序+容斥)
- hdu5468 Puzzled Elena(容斥原理+dfs序)
- HDU 5468 Puzzled Elena (容斥)
- hdu 5468 Puzzled Elena 预处理+深搜+容斥
- hdu 5468 Puzzled Elena
- 【HDU】5468 Puzzled Elena
- hdu5468 A Puzzled Elena (容斥原理)
- HDU 5468 Puzzled Elena (DFS序+莫比乌丝反演 好题)
- HDU 5468(Puzzled Elena-mobius+树形dp)
- hdu5468 Puzzled Elena(容斥 莫比乌斯反演)
- mobius HDOJ 5468 Puzzled Elena
- Puzzled Elena
- HDU 5468 Puzzled Elena (2015年上海赛区网络赛A题)
- HDU 5468 Puzzled Elena(2015 ACM/ICPC Asia Regional Shanghai Online)
- hdu 6001 容斥 + dfs
- hdu1796(容斥原理+最大公约数+DFS)
- DOS操作系统、常用DOS命令简介
- HDU 5491.The Next【2015 ACM/ICPC Asia Regional Hefei Online】【方法】【9月30】
- hdu 5458 Stability
- iOS开发之有趣的UI —— MVVM设计模式
- 如何使用xcode
- HDU 5468 Puzzled Elena(DFS序+容斥原理)
- 基本概念的认识
- 什么是类型安全
- C语言编程需要注意的64位和32机器的区别
- 《当幸福来敲门》观后感
- 基准测试
- 自己封装图片请求,好于SDWebImage,优化了UItableView(上)
- STM32 新建工程
- 《赢在中国》观后感