vjudge

Description

给一棵\(n\)个节点的有根树,定义两棵树同构当且仅当他们每个深度的节点个数相同。问这个树上有多少对子树满足同构。\(n\le100000\)。

sol

树\(hash\)。

每个深度的节点个数,类似于一个多项式?所以定义\(hash\)函数:

\[Hash(u)=base1+base2\sum Hash(v)
\]

最后判相等就不说了,\(sort\)一遍再搞一搞就好了。

code

在我交换\(base1\)和\(base2\)的值之前它是\(WA\)的。。。

#include<cstdio>
#include<algorithm>
#include<cstring>
using namespace std;
int gi(){
int x=0,w=1;char ch=getchar();
while ((ch<'0'||ch>'9')&&ch!='-') ch=getchar();
if (ch=='-') w=0,ch=getchar();
while (ch>='0'&&ch<='9') x=(x<<3)+(x<<1)+ch-'0',ch=getchar();
return w?x:-x;
}
#define ull unsigned long long
const int N = 2e5+5;
const ull base2 = 20020415;
const ull base1 = 20011118;
int n,to[N],nxt[N],head[N],cnt;
ull Hash[N],ans;
void link(int u,int v){
to[++cnt]=v;nxt[cnt]=head[u];head[u]=cnt;
}
void dfs(int u,int f){
Hash[u]=base1;
for (int e=head[u];e;e=nxt[e])
if (to[e]!=f) dfs(to[e],u),Hash[u]+=Hash[to[e]]*base2;
}
int main(){
n=gi();
for (int i=1;i<n;++i){
int u=gi(),v=gi();
link(u,v);link(v,u);
}
dfs(1,0);sort(Hash+1,Hash+n+1);
for (int i=1,j;i<=n;i=j){
j=i+1;
while (j<=n&&Hash[j]==Hash[i]) ++j;
ans+=1ll*(j-i)*(j-i-1)/2;
}
printf("%llu\n",ans);return 0;
}

最新文章

  1. JVM中对象的销毁
  2. gbd基本使用一
  3. 跟着鸟哥学Linux系列笔记3-第11章BASH学习
  4. ckedit 文本编辑器
  5. 解决vbox下安装centos不能上网问题
  6. 记录Cat类的个体数目
  7. MySQL数据库分布式事务XA优缺点与改进方案
  8. 解压和生成 system.img&amp;data.img ( ext4格式)
  9. C++操作符的优先级
  10. web项目的集成测试:模拟点击
  11. 201521123110《Java程序设计》第10周学习总结
  12. bzoj 2741
  13. php 的文件操作类
  14. Python 实现清屏
  15. blockdev命令 blkid命令 lsblk命令
  16. JScript 正则表达式语法表
  17. tf.equal的使用
  18. ROS学习笔记三(理解ROS节点)
  19. python中的list和array的不同之处 及转换
  20. HBase搭建部署

热门文章

  1. ZeroMq实现跨线程通信
  2. flutter自定义View(CustomPainter) 之 canvas的方法总结
  3. MongoDB 查看所有用户账号信息
  4. [myeclipse]@override报错问题
  5. OpenCL将数组从内存copy到显存
  6. 从HDC转换到leptonica PIX
  7. 小练习:Two Sum
  8. 029——VUE中键盘语义修饰符
  9. 基于centos的docker安装
  10. 初次使用Bootstrap