题意:给出一棵点带权的树,求i$\in$[1,200000]所有路径的上点权的gcd==i的个数。

考虑点分治,对于一棵以u为根的子树,如何统计经过u的路径的答案?

显然既然是经过点u的路径,那么所有经过u的路径上的点权的gcd肯定是点u的点权的约数。

暴力算下,2e5以内最多只有160个约数。

然后dfs出u子树里所有点到u路径的gcd,然后用个桶,最多\(u的点权的约数个数^2\)数下数就行了,但是实际应该是远远不满的。

最慢的一个点1404ms,4.5s的时限应该没什么问题。

然而这题的标签里有个dp(滑稽

//by zykykyk
#include<cstdio>
#include<algorithm>
#include<string>
#include<cstring>
#include<iostream>
using namespace std;
#define ll long long
#define For(i,x,y) for (register int i=(x);i<=(y);i++)
#define Dow(i,x,y) for (register int i=(x);i>=(y);i--)
#define cross(i,k) for (register int i=first[k];i;i=last[i])
inline ll read(){
ll x=0;int ch=getchar(),f=1;
while (!isdigit(ch)&&(ch!='-')&&(ch!=EOF)) ch=getchar();
if (ch=='-'){f=-1;ch=getchar();}
while (isdigit(ch)){x=(x<<1)+(x<<3)+ch-'0';ch=getchar();}
return x*f;
}
const int N = 2e5+10;
int n,x,y,Size,rt,a[N];
ll ans[N];
int tot,first[N],last[N<<1],to[N<<1];
inline void Add(int x,int y){to[++tot]=y,last[tot]=first[x],first[x]=tot;}
int size[N],Max[N];
bool vis[N];
inline void GetRoot(int u,int fa){
Max[u]=0,size[u]=1;
cross(i,u) if (to[i]!=fa&&!vis[to[i]]) GetRoot(to[i],u),size[u]+=size[to[i]],Max[u]=max(Max[u],size[to[i]]);
Max[u]=max(Max[u],Size-size[u]);
if (Max[rt]>Max[u]) rt=u;
}
int cnt,g[N];
ll b[N];
inline int gcd(int a,int b){return !b?a:gcd(b,a%b);}
inline void dfs(int u,int fa,int Gcd,int x,int rt){
if (x!=1||x==1&&u!=rt) g[++cnt]=Gcd,b[Gcd]++;
cross(i,u) if (to[i]!=fa&&!vis[to[i]]) dfs(to[i],u,gcd(Gcd,a[to[i]]),x,rt);
}
inline void solve(int u){
cnt=0,dfs(u,u,a[u],1,u),vis[u]=1;
sort(g+1,g+1+cnt);
int tot=unique(g+1,g+1+cnt)-g-1;
For(i,1,tot){
ans[g[i]]+=b[g[i]]+b[g[i]]*(b[g[i]]-1)/2;
For(j,i+1,tot) ans[gcd(g[i],g[j])]+=b[g[i]]*b[g[j]];
}
For(i,1,tot) b[g[i]]=0;
cross(k,u)
if (!vis[to[k]]){
cnt=0,dfs(to[k],u,gcd(a[u],a[to[k]]),0,to[k]);
sort(g+1,g+1+cnt);
int tot=unique(g+1,g+1+cnt)-g-1;
For(i,1,tot){
ans[g[i]]-=b[g[i]]*(b[g[i]]-1)/2;
For(j,i+1,tot) ans[gcd(g[i],g[j])]-=b[g[i]]*b[g[j]];
}
For(i,1,tot) b[g[i]]=0;
}
cross(i,u) if (!vis[to[i]]) Size=size[to[i]],rt=0,GetRoot(to[i],u),solve(rt);
}
int main(){
n=read();
For(i,1,n) a[i]=read(),ans[a[i]]++;
For(i,1,n-1) x=read(),y=read(),Add(x,y),Add(y,x);
Size=n,Max[0]=1e9,GetRoot(1,1),solve(rt);
For(i,1,N-10) if (ans[i]) printf("%d %lld\n",i,ans[i]);
}

Codeforces 990G 点分治+暴力的更多相关文章

  1. CodeForces - 990G (点分治+链表计数)

    题目:https://vjudge.net/contest/307753#problem/J 题意:一棵树,每个点都有个权值,现在问你,树上gcd每个不同的数有多少个 思路:点分治,首先范围只有 1e ...

  2. Codeforces Round #355 (Div. 2) D. Vanya and Treasure 分治暴力

    D. Vanya and Treasure 题目连接: http://www.codeforces.com/contest/677/problem/D Description Vanya is in ...

  3. codeforces 724B Batch Sort(暴力-列交换一次每行交换一次)

    题目链接:http://codeforces.com/problemset/problem/724/B 题目大意: 给出N*M矩阵,对于该矩阵有两种操作: (保证,每行输入的数是 1-m 之间的数且不 ...

  4. codeforces 897A Scarborough Fair 暴力签到

    codeforces 897A Scarborough Fair 题目链接: http://codeforces.com/problemset/problem/897/A 思路: 暴力大法好 代码: ...

  5. 【BZOJ 4059】 (分治暴力|扫描线+线段树)

    4059: [Cerc2012]Non-boring sequences Time Limit: 10 Sec  Memory Limit: 128 MBSubmit: 632  Solved: 22 ...

  6. Codeforces A. Playlist(暴力剪枝)

    题目描述: Playlist time limit per test 2 seconds memory limit per test 256 megabytes input standard inpu ...

  7. Codeforces 1101D 点分治

    题意:有一颗树,每个点有一个点权,边权都是1,问路径上的所有点的gcd不是1的最长路径是多少? 思路:之前补这道题的时候,用分解质因数 + 树形DP做的,其实用点分治可以更暴力一点.对于这类统计树上路 ...

  8. Codeforces 293E 点分治+cdq

    Codeforces 293E 传送门:https://codeforces.com/contest/293/problem/E 题意: 给你一颗边权一开始为0的树,然后给你n-1次操作,每次给边加上 ...

  9. codeforces 161D 点分治

    传送门:https://codeforces.com/problemset/problem/161/D 题意: 求树上点对距离恰好为k的点对个数 题解: 与poj1741相似 把点分治的模板改一下即可 ...

随机推荐

  1. CodeForces 1011B

    Description Natasha is planning an expedition to Mars for nn people. One of the important tasks is t ...

  2. APP爬虫之Appium使用

    一.安装环境 Appium安装(windows版) 一.安装node.js 1.到官网下载node.js:https://nodejs.org/en/download/ 2.获取到安装文件后,直接双击 ...

  3. 使用Burpsuite爆破弱口令教工号

    使用Burpsuite爆破弱口令教工号 发表于 2015-11-18   |   分类于 Burpsuite  |   1条评论  |   26次阅读 准备 所谓工欲善其事,必先利其器,首先当然是要下 ...

  4. 35 - 并发编程-GIL-多进程

    目录 1 GIL 1.1 为什么会有GIL 1.2 GIL与thread lock 1.3 个人总结 2 multiprocessing模块 2.1 Process类 2.2 Process类的方法 ...

  5. 如何在LINUX中开机、登陆、退出、定时、定期自动运行程序

    1.开机启动时自动运行程序 Linux加载后, 它将初始化硬件和设备驱动, 然后运行第一个进程init.init根据配置文件继续引导过程,启动其它进程.通常情况下,修改放置在 /etc/rc或 /et ...

  6. git 还原到指定版本号

      git clone git branch -r --contains 88b92060224e96ef209565fa75c816eb9b0fae8e git checkout origin/re ...

  7. Django项目上传到AWS服务器上

    EC2是亚马逊(Amazon.com)提供的弹性云计算服务:Apache是一个跨平台的Web服务器端软件,可以使Python.PHP.Perl等语言编写的程序运行在服务器上:Django是一个Web程 ...

  8. Erasure Coding(纠删码)深入分析 转

    1.前言 Swift升级到2.0大版本后宣称开始支持纠删码,这其实是一个很有意义的特性,主要是能够在一定程度上解决3副本空间浪费太多的问题.因为3副本这一点是swift推广的最大障碍之一,成本的增加吓 ...

  9. [前端随笔][JavaScript] 制作一个富文本编辑器

    写在前面 现在网上有很多现成的富文本编辑器,比如百度家的UEditor,kindeditor,niceditor等等,功能特别的多,API也很多,要去熟悉他的规则也很麻烦,所以想自己了解一下原理,做一 ...

  10. 响应式之像素和viewport

    引言 按照pc尺寸做好的网页,在手机端打开,看起来像是pc的缩小版,东西都在只是字太小都看不清了,有什么办法放大呢? 于是去google一下,发现,贴了这么一行代码就轻松解决了: <meta n ...