YbtOJ#20081-[NOIP2020模拟赛B组Day8]树上排列【组合数,树形dp】
正题
题面链接:https://www.ybtoj.com.cn/contest/62/problem/3
题目大意
nnn个点的一棵树,每个边的边会表示一个大小关系(如px>pyp_x>p_ypx>py或px<pyp_x<p_ypx<py)。求有多少个排列满足所有条件。
解题思路
考虑树形dpdpdp,设fi,jf_{i,j}fi,j表示点iii的子树中有jjj个比他小的数字时的方案数。
那么如果有条件py<pxp_y<p_xpy<px考虑如何转移,我们枚举一下i,ji,ji,j表示之前比iii小的数的个数和yyy里面比xxx小的个数,然后再枚举一个kkk表示yyy里面比yyy小的数的个数。
然后用组合数插板表示方案,发现这样是O(n3)O(n^3)O(n3)的,发现kkk可以前/后缀和优化,所以可以缩掉,时间复杂度为O(n2)O(n^2)O(n2)
codecodecode
#include<cstdio>
#include<cstring>
#include<algorithm>
#define ll long long
using namespace std;
const ll N=5100,XJQ=998244353;
struct node{ll to,next,w;
}a[N*2];
ll n,tot,ls[N],c[N][N],f[N][N],g[N],siz[N],ans;
ll C(ll n,ll m){return c[n+1][m+1];}
void addl(ll x,ll y,ll w){a[++tot].to=y;a[tot].next=ls[x];ls[x]=tot;a[tot].w=w;return;
}
void dfs(ll x,ll fa){f[x][0]=1;siz[x]=1;for(ll p=ls[x];p;p=a[p].next){ll y=a[p].to;if(y==fa)continue;dfs(y,x);for(ll i=0;i<=siz[x]+siz[y];i++)g[i]=0;if(a[p].w){for(ll i=0;i<siz[x];i++){ll tmp=0;for(ll j=siz[y]-1;j>=0;j--){ll px=i,py=j;tmp=(tmp+f[y][j])%XJQ;ll sx=siz[x]-i-1,sy=siz[y]-j-1;(g[siz[x]+siz[y]-sx-sy-2]+=f[x][i]*tmp%XJQ*C(sx+sy+1,sx)%XJQ*C(px+py,py)%XJQ)%=XJQ;}}}else{for(ll i=0;i<siz[x];i++){ll tmp=0;for(ll j=0;j<siz[y];j++){ll px=i,py=j;tmp=(tmp+f[y][j])%XJQ;ll sx=siz[x]-i-1,sy=siz[y]-j-1;(g[px+py+1]+=f[x][i]*tmp%XJQ*C(px+py+1,px)%XJQ*C(sx+sy,sy)%XJQ)%=XJQ;}}}siz[x]+=siz[y];for(ll i=0;i<=siz[x];i++)f[x][i]=g[i];}return;
}
int main()
{freopen("perm.in","r",stdin);freopen("perm.out","w",stdout);scanf("%lld",&n);for(ll i=1;i<n;i++){ll x,y;scanf("%lld%lld",&x,&y);addl(x,y,0);addl(y,x,1);}c[0][0]=1;for(ll i=1;i<N;i++)for(ll j=1;j<N;j++)c[i][j]=(c[i-1][j]+c[i-1][j-1])%XJQ;dfs(1,1);for(ll i=0;i<siz[1];i++)(ans+=f[1][i])%=XJQ;printf("%lld\n",ans);
}
YbtOJ#20081-[NOIP2020模拟赛B组Day8]树上排列【组合数,树形dp】相关推荐
- YbtOJ#20239-[冲刺NOIP2020模拟赛Day10]连边方案【状压dp】
正题 题目链接:https://www.ybtoj.com.cn/contest/68/problem/3 题目大意 求有多少个nnn个点mmm条边的无向图满足 有连边的点之间编号差不超过kkk 所有 ...
- YbtOJ#20064-[NOIP2020模拟赛B组Day4]预算缩减【树形dp】
正题 题目链接:http://noip.ybtoj.com.cn/contest/90/problem/2 题目大意 nnn个点的一棵树,求删掉一些边让剩下的连通块大小不小于kkk,求方案数. 解题思 ...
- YbtOj#20073. 「NOIP2020 模拟赛 B 组 Day6」钻石守卫
文章目录 ResultResultResult HyperlinkHyperlinkHyperlink DescriptionDescriptionDescription SolutionSoluti ...
- YbtOJ#20082-[NOIP2020模拟赛B组Day8]导出子图【dp】
正题 题面链接:https://www.ybtoj.com.cn/contest/62/problem/4 题目大意 nnn个区间,如果第xxx个区间和第yyy个区间有交集那么xxx到yyy直接就有一 ...
- YbtOJ#20237-[冲刺NOIP2020模拟赛Day10]区间均值【树状数组】
正题 题目链接:https://www.ybtoj.com.cn/contest/68/problem/1 题目大意 nnn个数字的序列,求有多少个区间[l,r][l,r][l,r]的平均值在[L,R ...
- YbtOJ#20240-[冲刺NOIP2020模拟赛Day10]弱者对决【笛卡尔树,区间dp】
正题 题目链接:https://www.ybtoj.com.cn/contest/68/problem/4 题目大意 mmm个三元组(ai,bi,ci)(a_i,b_i,c_i)(ai,bi,ci ...
- YbtOJ#20236-[冲刺NOIP2020模拟赛Day9]红点蓝点【线段树,堆】
正题 题目链接:https://www.ybtoj.com.cn/contest/66/problem/4 题目大意 平面上nnn个红点,nnn个蓝点,对于没一个红点求一个与它纵坐标距离不超过ddd的 ...
- YbtOJ#20235-[冲刺NOIP2020模拟赛Day9]公共序列【dp】
正题 题目链接:https://www.ybtoj.com.cn/contest/66/problem/3 题目大意 给出两个字符串A,BA,BA,B,求它们的最长公共子序列. 解题思路 先考虑朴素的 ...
- YbtOj 冲刺 NOIP2020 模拟赛 Day10 T1 区间均值
文章目录 ResultResultResult HyperlinkHyperlinkHyperlink DescriptionDescriptionDescription SolutionSoluti ...
最新文章
- 浅谈CMMI几个过程概念流程管理 (转)
- IOS UITableView性能优化
- android Activity runOnUiThread() 方法使用
- 寻找mysql的data文件夹得方式
- redux 源码详解
- linux内核PID管理
- Entity Framework Fluent API
- java变量和常量_java变量和常量的区别是什么
- CMD应用 qtp/winshell/cmd的交互
- MongoDB学习(黑马教程)-5-数据库MongoDB的验证
- c# pdf转html,C# 将PDF转为Word、Html、XPS、SVG、PCL、PS——基于Spire.Cloud.PDF
- wince之浅谈无线漫游
- 最新服务器处理器天梯,2019 最新 至强 Xeon 服务器系列 CPU天梯图
- 怎样更改计算机文件名,电脑如何批量修改文件名|批量修改文件名的几个小方法...
- JAVA中计算五子棋平局的算法_输入五子棋棋盘判断输赢或平局—程序设计(C语言)...
- 第四回:产品创新性思维方法论
- 一级建造师考试报名需要的材料,点击收藏!
- python爬虫豆瓣电影评价_Python 爬虫实战(1):分析豆瓣中最新电影的影评
- ImageJ对荧光信号离散的细胞计数方法
- 重构改善代码--代码的坏味道
热门文章
- abs函数的使用方法 oracle_SQL Server 常用函数使用方法
- python离群点检测_如何从熊猫DataFrame中检测峰点(离群值)
- mysql查询语句4,MySQL(4):CRUD语句(2)——基本查询
- Jdbc创建表 利用循环添加数据 ,更新数据
- android system window,Android之属性fitsSystemWindows
- [Redis6]新数据类型_HyperLogLog
- python提取文件名的5-6位_python提取文件名
- word List36
- JVM(1)——JVM内存分区
- SpringMVC 、Struts的区别