Appleman and Tree

题解:

定义dp[u][1] 为以u的子树范围内,u这个点已经和某个黑点相连的方案数。

dp[u][0] 为在u的子树范围内, u这个点还未和某个黑点相连的方案数。

转移方程:

如果 u为黑点, dp[u][0] = 0, dp[u][1] = 1, 然后考虑从下面转移过来, dp[u][1] *= dp[v][0] + dp[v][1].

也就是说, 如果 v 点为黑,则切断这个边, 如果v点为白,则不切断, 即对于v来说,每个情况,切边的情况也只有一种, 不同的v的方案数相互独立。

如果 u为白点, dp[u][0] = 1, dp[u][1] = 1, 考虑转移 dp[u][0] *= dp[v][0] + dp[v][1], dp[u][1] += dp[v][1] * (除v以外的子树(dp[z][1] + dp[z][0])乘积 。

对于dp[u][0]来说,和上面的道理一样。

对于dp[u][1]来说,枚举和下面哪一个黑点连边,然后这个点对于其他的v来说就相当于一个黑点,转移的方程就是和 u 是黑点的道理一样了。

代码:

#include<bits/stdc++.h>
using namespace std;
#define Fopen freopen("_in.txt","r",stdin); freopen("_out.txt","w",stdout);
#define LL long long
#define ULL unsigned LL
#define fi first
#define se second
#define pb push_back
#define lson l,m,rt<<1
#define rson m+1,r,rt<<1|1
#define lch(x) tr[x].son[0]
#define rch(x) tr[x].son[1]
#define max3(a,b,c) max(a,max(b,c))
#define min3(a,b,c) min(a,min(b,c))
typedef pair<int,int> pll;
const int inf = 0x3f3f3f3f;
const int _inf = 0xc0c0c0c0;
const LL INF = 0x3f3f3f3f3f3f3f3f;
const LL _INF = 0xc0c0c0c0c0c0c0c0;
const LL mod = (int)1e9+;
const int N = 1e5 + ;
vector<int> vc[N];
int dp[N][];
int pre[N], suf[N];
int a[N];
void dfs(int u){
if(a[u] == ) {
dp[u][] = ; dp[u][] = ;
for(int v : vc[u]){
dfs(v);
dp[u][] = (1ll * dp[u][] * (dp[v][] + dp[v][])) % mod;
}
}
else{
dp[u][] = ; dp[u][] = ;
int t = vc[u].size();
for(int v : vc[u]){
dfs(v);
}
for(int i = ; i < t; ++i){
int v = vc[u][i];
suf[i+] = pre[i+] = (dp[v][]+dp[v][]) % mod;
}
pre[] = ; suf[t+] = ;
for(int i = ; i <= t; ++i)
pre[i] = 1ll * pre[i] * pre[i-] % mod;
for(int i = t; i >= ; --i)
suf[i] = 1ll * suf[i] * suf[i+] % mod;
dp[u][] = pre[t];
for(int i = ; i <= t; ++i){
int v = vc[u][i-];
dp[u][] = (dp[u][] + 1ll * dp[v][] * (1ll * pre[i-] * suf[i+]%mod))% mod;
}
}
}
int main(){
int n, o;
scanf("%d", &n);
for(int i = ; i <= n; ++i){
scanf("%d", &o);
vc[o+].pb(i);
}
for(int i = ; i <= n; ++i)
scanf("%d", &a[i]);
dfs();
printf("%d\n", dp[][]);
return ;
}

最新文章

  1. 跳转到某个Activity
  2. Happy Programming Contest(ZOJ3703)(01背包+路径储存)
  3. 【转载】ASP.NET MVC Web API 的路由选择
  4. 智者当借力而行, 借助Autodesk应用程序商店实现名利双收
  5. PostgreSQL中initdb做了什么
  6. android学习笔记42——图形图像处理2——绘图
  7. hdu 2425 Hiking Trip
  8. Servlet、Struts2、SpringMVC执行流程
  9. 使用cwRsync实现windows下文件定时同步【转】
  10. select--from--where--group by--having--order by 依次顺序
  11. BestCoder Sequence
  12. FirstOrDefault
  13. JavaScript 将字符串转化为json对象
  14. 寒假的ACM训练(一)
  15. iostat 使用说明
  16. ios文件读取
  17. 修改Eclipse的WorkSpace保持数[转载]
  18. Delphi中复制带有String的记录结构时不能使用Move之类的内存操作函数
  19. C# 在本地创建文件夹及子文件夹
  20. 某里巴巴Java工程师常规面试题以及解答

热门文章

  1. Mac Android 配置环境变量
  2. iOS 注释
  3. Mac 10.14.4 编译openjdk1.9源码 及集成clion动态调试
  4. 从原理层面掌握@SessionAttribute的使用【一起学Spring MVC】
  5. bat 搜索进程名并kill
  6. idea 新建不了servlet文件 方法(1)
  7. 【0730 | Day 4】Python基础(二)
  8. (八)c#Winform自定义控件-分割线
  9. 建立apk定时自动打包系统第二篇——自动上传文件
  10. 小白学Python(6)——python-pptx 添加图表