hdu5909 Tree Cutting 【树形dp + FWT】
题目链接
题解
设\(f[i][j]\)表示以\(i\)为根的子树,\(i\)一定取,剩余节点必须联通,异或和为\(j\)的方案数
初始化\(f[i][val[i]] = 1\)
枚举儿子\(v\)转移
\]
发现是一个异或卷积的形式
前面相当于和\(1\)的卷积,后面是和\(f[v]\)的卷积
\(FWT\)即可优化到\(O(nlogn + nm)\)
我被卡常了QAQ,需要注意一些细节
单独一个\(1\)做\(FWT\)是全\(1\),转移乘\(f[v][j]\)时\(+1\)即可
每个\(f[i]\)做完\(FWT\)后不立即\(IFWT\),可以直接参与转移,全部做完后再\(IFWT\)
循环展开大法好
#include<algorithm>
#include<iostream>
#include<cstdlib>
#include<cstring>
#include<cstdio>
#include<vector>
#include<queue>
#include<cmath>
#include<map>
#define LL long long int
#define REP(i,n) for (register int i = 1; i <= (n); i++)
#define Redge(u) for (register int k = h[u],to; k; k = ed[k].nxt)
#define cls(s,v) memset(s,v,sizeof(s))
#define mp(a,b) make_pair<int,int>(a,b)
#define cp pair<int,int>
using namespace std;
const int maxn = 2050,maxm = 100005,INF = 0x3f3f3f3f;
inline int read(){
int out = 0,flag = 1; char c = getchar();
while (c < 48 || c > 57){if (c == '-') flag = 0; c = getchar();}
while (c >= 48 && c <= 57){out = (out << 1) + (out << 3) + c - 48; c = getchar();}
return flag ? out : -out;
}
const int P = 1000000007;
int n,m,deg,val[maxn],A[maxn][maxn],B[maxn],inv2,fa[maxn];
int h[maxn],ne = 1;
struct EDGE{int to,nxt;}ed[maxn << 1];
inline void build(int u,int v){
ed[++ne] = (EDGE){v,h[u]}; h[u] = ne;
ed[++ne] = (EDGE){u,h[v]}; h[v] = ne;
}
inline int qpow(int a,int b){
int re = 1;
for (; b; b >>= 1,a = 1ll * a * a % P)
if (b & 1) re = 1ll * re * a % P;
return re;
}
inline void fwt(int* a,int n,int f){
for (int i = 1; i < n; i <<= 1)
for (int j = 0; j < n; j += (i << 1))
for (int k = 0; k < i; k++){
int x = a[j + k],y = a[j + k + i];
a[j + k] = (x + y) % P,a[j + k + i] = (x - y + P) % P;
if (f == -1) a[j + k] = 1ll * a[j + k] * inv2 % P,a[j + k + i] = 1ll * a[j + k + i] * inv2 % P;
}
}
void dfs(int u){
for (register int i = 0; i < deg; i += 4){
A[u][i] = 0; A[u][i + 1] = 0;
A[u][i + 2] = 0; A[u][i + 3] = 0;
}
A[u][val[u]] = 1; fwt(A[u],deg,1);
Redge(u) if ((to = ed[k].to) != fa[u]){
fa[to] = u; dfs(to);
for (register int i = 0; i < deg; i++)
A[u][i] = 1ll * A[u][i] * (A[to][i] + 1) % P;
}
}
int main(){
int T = read(); inv2 = qpow(2,P - 2);
while (T--){
n = read(); m = read(); deg = 1; ne = 1;
REP(i,n) h[i] = 0;
while (deg < m) deg <<= 1;
REP(i,n) val[i] = read();
for (int i = 1; i < n; i++) build(read(),read());
dfs(1);
REP(i,n) fwt(A[i],deg,-1);
for (register int i = 0; i < m; i++){
int ans = 0;
for (register int j = 1; j <= n; j++) ans = (ans + A[j][i]) % P;
printf("%d",ans);
if (i != m - 1) putchar(' ');
}
puts("");
}
return 0;
}
hdu5909 Tree Cutting 【树形dp + FWT】的更多相关文章
- hdu 5909 Tree Cutting [树形DP fwt]
hdu 5909 Tree Cutting 题意:一颗无根树,每个点有权值,连通子树的权值为异或和,求异或和为[0,m)的方案数 \(f[i][j]\)表示子树i中经过i的连通子树异或和为j的方案数 ...
- HDU - 5909 Tree Cutting (树形dp+FWT优化)
题意:树上每个节点有权值,定义一棵树的权值为所有节点权值异或的值.求一棵树中,连通子树值为[0,m)的个数. 分析: 设\(dp[i][j]\)为根为i,值为j的子树的个数. 则\(dp[i][j\o ...
- HDU.5909.Tree Cutting(树形DP FWT/点分治)
题目链接 \(Description\) 给定一棵树,每个点有权值,在\([0,m-1]\)之间.求异或和为\(0,1,...,m-1\)的非空连通块各有多少个. \(n\leq 1000,m\leq ...
- POJ 2378.Tree Cutting 树形dp 树的重心
Tree Cutting Time Limit: 1000MS Memory Limit: 65536K Total Submissions: 4834 Accepted: 2958 Desc ...
- [poj3107/poj2378]Godfather/Tree Cutting树形dp
题意:求树的重心(删除该点后子树最大的最小) 解题关键:想树的结构,删去某个点后只剩下它的子树和原树-此树所形成的数,然后第一次dp求每个子树的节点个数,第二次dp求解答案即可. 此题一开始一直T,后 ...
- poj 2378 Tree Cutting 树形dp
After Farmer John realized that Bessie had installed a "tree-shaped" network among his N ( ...
- HDU5834 Magic boy Bi Luo with his excited tree(树形DP)
题目 Source http://acm.hdu.edu.cn/showproblem.php?pid=5834 Description Bi Luo is a magic boy, he also ...
- BZOJ-3227 红黑树(tree) 树形DP
个人认为比较好的(高端)树形DP,也有可能是人傻 3227: [Sdoi2008]红黑树(tree) Time Limit: 10 Sec Memory Limit: 128 MB Submit: 1 ...
- Codeforces Round #263 (Div. 2) D. Appleman and Tree(树形DP)
题目链接 D. Appleman and Tree time limit per test :2 seconds memory limit per test: 256 megabytes input ...
- 2017 Multi-University Training Contest - Team 1 1003&&HDU 6035 Colorful Tree【树形dp】
Colorful Tree Time Limit: 6000/3000 MS (Java/Others) Memory Limit: 131072/131072 K (Java/Others)T ...
随机推荐
- OpenGL学习笔记(6) 基础光照的计算方法
这个笔记只是冯氏光照模型下漫反射光以及镜面光照的计算方式的笔记 基础光照 基础光照分为环境光,漫反射光,镜面光照 环境光 环境光是一个常量,表示在没有光源的情况下物体的光 漫反射光 漫反射光分量的计算 ...
- MYSQL 数据库结构优化
数据库结构优化 优化数据大小 使表占用尽量少的磁盘空间.减少磁盘I/O次数及读取数据量是提升性能的基础原则.表越小,数据读写处理时则需要更少的内存,同时,小表的索引占用也相对小,索引处理也更加快速. ...
- 4.three.js中的坐标系
Three.js中的坐标系 three.js中坐标系使用的是左手坐标系 左手坐标系和右手坐标系的对比: 当然three.js中使用的是右手坐标系 three.js中的旋转的定义 但是three.js中 ...
- WebRtc与SIP
最近研究一下 webrtc ,看了几篇paper,之前也尝试运行验证了几个demo,现在把我的理解总结到这里. WebRTC 简介 WebRTC,名称源自网页实时通信(Web Real-Time Co ...
- 为什么找程序员一定要看他的 GitHub
听说 最开始听到这句话是某知名互联网公司大牛告诉我的,我很不以为然,不过迫于他是"leader"我也注册了一个 highsea (广告 0.0):当然我可懒得 push 更别提 c ...
- 5233杨光--Linux第二次实验
实验说明 1. 环境登录 无需密码自动登录,系统用户名shiyanlou,密码shiyanlou 若不小心登出后,直接刷新页面即可 2. 环境使用 完成实验后可以点击桌面上方的“实验截图”保存并分享实 ...
- c# combobox向上展开
1.问题情境:实际中的下拉框默认向下扩展,如果屏幕下方空间不足,会向上扩展. 向下扩展情况下,有时候会超出form窗体. 2.解决办法: 寻找相关属性无果. 退而求其次,重画item的框.发现Draw ...
- html border画三角形
最近遇到了问题就是画推进条类似于
- static 继承
静态方法大家应该都比较熟悉,在这里主要谈一下静态方法在继承时的一些注意事项. 1.父类方法如果是静态方法,子类不能覆盖为非静态方法: 2.父类方法如果是非静态方法,子类不能覆盖为静态方法: 3.父类静 ...
- Oracle安装后出现的问题
安装oracle没有勾选"安装模板数据库",可以通过执行以下命令进行修改: cd $ORACLE_HOME/rdbms/admin 到这个目录下sqlplus /as sysdba ...