Atcoder Grand Contest 024 E - Sequence Growing Hard(dp+思维)
典型的 Atcoder 风格的计数 dp。
题目可以转化为每次在序列中插入一个 \([1,k]\) 的数,共操作 \(n\) 次,满足后一个序列的字典序严格大于前一个序列,问有多少种操作序列。
显然相同的数可以合并,因为在由相同的数 \(x\) 组成的数段中,在任何位置插入 \(x\),得到的序列都是相同的。
再考虑字典序的问题。你只能序列末尾或者一个 \(<x\) 的数前面插入 \(x\),否则得到的序列的字典序就会 \(\geq\) 原序列的字典序。
但这样问题还是比较棘手,我们还需进一步转化。
我们把操作序列转化为一棵有根树,树上每个节点都是一个二元组 \((val,dfn)\),表示第 \(dfn\) 次操作插入了值为 \(val\) 的数。如果第 \(i\) 次操作将 \(v\) 插在第 \(j\) 次操作插入的数 \(w\) 前面,那么我们就将节点 \((v,i)\) 挂在 \((w,j)\) 下面。新建一个虚拟节点 \((0,0)\),如果在序列末尾插入 \(v\),那么就把 \((v,i)\) 挂在 \((0,0)\) 下面。
由于我们只能在 \(<x\) 的数前面插入 \(x\),因此若 \(y\) 为 \(x\) 的父亲,那么 \(val_y>val_x\),\(dfn_y<dfn_x\)
不妨举个例子,假设有如下的操作序列:
- 向序列中插入数 \(1\),得到序列 \([1]\)。这可看成将点 \((1,1)\) 挂在点 \((0,0)\) 下面。
- 在 \(1\) 前插入 \(3\),得到序列 \([3,1]\)。这可看成将点 \((3,2)\) 挂在点 \((1,1)\) 下面。
- 在序列末尾插入 \(2\),得到序列 \([3,1,2]\)。这可看成将点 \((2,3)\) 挂在点 \((0,0)\) 下面。
- 在 \(1\) 再插入一个 \(3\),得到序列 \([3,3,1,2]\)。这可看成将点 \((3,4)\) 挂在点 \((1,1)\) 下面。
- 在 \(1\) 前插入一个 \(2\),得到序列 \([3,3,2,1,2]\)。这可看成将点 \((2,5)\) 挂在点 \((1,1)\) 下面。
- 在第二个 \(3\) 前插入一个 \(4\),得到序列 \([3,4,3,2,1,2]\)。这可看成将点 \((4,6)\) 挂在点 \((3,4)\) 下面。
这样 \(6\) 次操作下来,我们得到了一棵 \(7\) 个节点的树,如下图:

一种操作序列恰对应一棵树,一棵满足条件的树也对应一种操作序列。因此问题转化为有多少个满足条件的树。
这就可以直接 \(dp\) 了。我们设 \(dp_{i,j}\) 表示有多少个以 \(i\) 为节点的树,根节点的 \(val\) 为 \(j\)。
考虑转移,对于 \(i>1\),假设根节点的 \(dfn\) 为 \(1\),那么根节点必定有个儿子,其 \(dfn\) 为 \(2\)。我们就枚举这棵子树的大小 \(l\) 和根节点的 \(val\) —— \(v\)。确定这棵子树的形态的方案数为 \(dp_{l,v}\),将这棵子树中所有节点的 \(dfn\) 值定好的方案数为 \(C_{n-2}^{k-1}\)(从 \(3\) 到 \(n\) 这 \(n-2\) 个数中中选择 \(k-1\) 个数),填好剩余部分的方案数为 \(dp_{i-l,j}\)。因此有转移方程:
\]
后面那个 \(\sum\) 可以用前缀和优化掉。时间复杂度 \(\mathcal O(n^2k)\)
/*
Contest: -
Problem: Atcoder Grand Contest 024 E
Author: tzc_wk
Time: 2020.7.22
*/
#include <bits/stdc++.h>
using namespace std;
#define fi first
#define se second
#define fz(i,a,b) for(int i=a;i<=b;i++)
#define fd(i,a,b) for(int i=a;i>=b;i--)
#define foreach(it,v) for(__typeof(v.begin()) it=v.begin();it!=v.end();it++)
#define all(a) a.begin(),a.end()
#define fill0(a) memset(a,0,sizeof(a))
#define fill1(a) memset(a,-1,sizeof(a))
#define fillbig(a) memset(a,0x3f,sizeof(a))
#define fillsmall(a) memset(a,0xcf,sizeof(a))
#define y1 y1010101010101
#define y0 y0101010101010
#define int long long
typedef pair<int,int> pii;
inline int read(){
int x=0,neg=1;char c=getchar();
while(!isdigit(c)){
if(c=='-') neg=-1;
c=getchar();
}
while(isdigit(c)) x=x*10+c-'0',c=getchar();
return x*neg;
}
int n=read(),k=read(),m=read();
int C[305][305],s[305][305],dp[305][305];
signed main(){
fz(i,0,300){
C[i][0]=1;
fz(j,1,i) C[i][j]=(C[i-1][j]+C[i-1][j-1])%m;
}
// printf("%d\n",C[5][3]);
fz(i,0,k) dp[1][i]=1;
fd(i,k,0) s[1][i]=(s[1][i+1]+dp[1][i])%m;
fz(i,2,n+1){
fz(j,0,k)
fz(l,1,i-1)
dp[i][j]=(dp[i][j]+C[i-2][l-1]*dp[i-l][j]%m*s[l][j+1]%m)%m;
fd(j,k,0) s[i][j]=(s[i][j+1]+dp[i][j])%m;
}
printf("%lld\n",dp[n+1][0]);
return 0;
}
Atcoder Grand Contest 024 E - Sequence Growing Hard(dp+思维)的更多相关文章
- AtCoder Grand Contest 019 B - Reverse and Compare【思维】
AtCoder Grand Contest 019 B - Reverse and Compare 题意:给定字符串,可以选定任意i.j且i<=j(当然i==j时没啥卵用),然后翻转i到j的字符 ...
- [AtCoder Grand Contest 024 Problem E]Sequence Growing Hard
题目大意:考虑 N +1 个数组 {A0,A1,…,AN}.其中 Ai 的长度是 i,Ai 内的所有数字都在 1 到 K 之间. Ai−1 是 Ai 的子序列,即 Ai 删一个数字可以得到 Ai−1. ...
- Atcoder Grand Contest 024
A 略 B 略 C 略 D(构造分形) 题意: 给出一个由n个点的组成的树,你可以加一些点形成一个更大的树.对于新树中的两个点i和j,如果以i为根的树与以j为根的树是同构的那么i和j颜色可以相同.问最 ...
- Atcoder Grand Contest 005 E - Sugigma: The Showdown(思维题)
洛谷题面传送门 & Atcoder 题面传送门 记先手移动棋子的树为红树,后手移动棋子的树为蓝树. 首先考虑一个性质,就是如果与当前红色棋子所在的点相连的边中存在一条边,满足这条边的两个端点在 ...
- Atcoder Grand Contest 022 E - Median Replace(dp)
Atcoder 题面传送门 & 洛谷题面传送门 首先考虑对于固定的 01 串怎样计算它是否可以通过将三个连续的 \(0\) 或 \(1\) 替换为其中位数得到.我们考虑单调栈,新建一个栈,栈底 ...
- Atcoder Grand Contest 002 F - Leftmost Ball(dp)
Atcoder 题面传送门 & 洛谷题面传送门 这道 Cu 的 AGC F 竟然被我自己想出来了!!!((( 首先考虑什么样的序列会被统计入答案.稍微手玩几组数据即可发现,一个颜色序列 \(c ...
- Atcoder Grand Contest 039C(容斥原理,计数DP)
//每次操作相当于将最低位取反加到最高位(N~1位)#define HAVE_STRUCT_TIMESPEC#include<bits/stdc++.h>using namespace s ...
- Atcoder Grand Contest 037C(贪心,优先队列,思维)
#define HAVE_STRUCT_TIMESPEC//编译器中time.h和phread.h头文件中timespec结构体重名,故加此行#include<bits/stdc++.h> ...
- AtCoder Grand Contest 031 简要题解
AtCoder Grand Contest 031 Atcoder A - Colorful Subsequence description 求\(s\)中本质不同子序列的个数模\(10^9+7\). ...
随机推荐
- OO第三单元
OO第三单元 JML语言理论基础,应用工具链 JML语言基础 JML简介 定义: JML 是一种形式化的. 面向 JAVA 的行为接口规格语言 作用: 开展规格化设计.这样交给代码实现人员的将不是可能 ...
- mac上安装lua
一.背景 最近在操作redis的时候,有些时候是需要原子操作的,而redis中支持lua脚本,因此为了以后学习lua,此处记录一下 lua的安装. 二.mac上安装lua 其余的系统上安装lua步骤大 ...
- Noip模拟81 2021.10.20
T1 语言 比较简单的题,然后就瞎写了,所以考场上就我一个写了线段树的,所以我的常数.... 所以就枚举动词的位置,找前面后面有没有出现$4$即可 1 #include<bits/stdc++. ...
- linked-list-cycle-ii leetcode C++
Given a linked list, return the node where the cycle begins. If there is no cycle, returnnull. Follo ...
- openstack 虚机热迁移问题:虚机状态一直处于迁移中的情况处理
前提:在偶尔的虚机热迁移中,发现虚机一直属于迁移状态中. 但是查看后台流量监控,发现没有流量已经下来了.然后在目标机器上查看,发现kvm已经在目标机器上. 1.查看kvm 实际所处宿主机方法: a.拿 ...
- centos 下安装docker
官方文档比较累赘,简化就三步 1.安装依赖 yum -y install gcc gcc-c++ yum-utils device-mapper-persistent-data lvm2 2.添加re ...
- seq2seq之双向解码
目录 背景介绍 双向解码 基本思路 数学描述 模型实现 训练方案 双向束搜索 代码参考 思考分析 文章小结 在文章<玩转Keras之seq2seq自动生成标题>中我们已经基本探讨过seq2 ...
- linux网络编程 IO多路复用 select epoll
本文以我的小型聊天室为例,对于服务器端的代码,做了三次改进,我将分别介绍阻塞式IO,select,epoll . 一:阻塞式IO 对于聊天室这种程序,我们最容易想到的是在服务器端accept之后,然后 ...
- MYSQL5.7下载安装图文教程
MYSQL5.7下载安装图文教程 一. MYSQL两种安装包格式 MySQL安装文件分为两种,一种是msi格式的,一种是zip格式的.zip格式相当于绿色版,不需要安装,只需解压缩之后就可以使用了,但 ...
- string类运用:特殊的翻译
特殊的翻译 小明的工作是对一串英语字符进行特殊的翻译:当出现连续且相同的小写字母时,须替换成该字母的大写形式,在大写字母的后面紧跟该小写字母此次连续出现的个数:与此同时,把连续的小写字母串的左侧和右侧 ...