Codeforces 960G. Bandit Blues
Description
你需要构造一个长度为 \(n\) 的排列 , 使得一个数作为前缀最大值的次数为 \(A\) , 作为后缀最大值的次数为 \(B\) , 求满足要求的排列个数 .
题面
Solution
同 \(FJOI\) 建筑师 .
从 \(n\) 到 \(1\) 依次加入 , 对于 \(n\) ,对 \(A,B\) 的出现次数都会贡献 \(1\) .
剩下的数 , 如果放在左边则对 \(A\) 有贡献 , 放在右边则对 \(B\) 有贡献 , 放在中间则没有贡献 .
我们从组合意义上分析 , 那么相当于是操作 \(n-1\) 轮 , 每轮可以选择 从 \((0,0)\) 向走 \((A-1,B-1)\) 一步或者停顿的方案数 .
从 \((0,0)\) 走向 \((A-1,B-1)\) 的不同方案数为 \(C(A+B-2,A-1)\)
并且还要求出分配停顿的位置(确定每个位置停了几次)的不同方案数 .
这个可以 \(DP\) 设前 \(i\) 次操作 , 走了 \(j\) 步的方案数, \(f[i][j]=f[i-1][j-1]+f[i-1][j]*(i-1)\) , 这个东西就等于第一类斯特林数 .
由于\(S(n,m)\)等于 \(P(x,n)\) 的第 \(x^m\) 项系数 , 就可以对应一个上升幂的 \(x^m\) 项系数.
可以分治+\(NTT\) 合并出一个长度为 \(n\) 的多项式 , 就可以求出第一类斯特林数的某一行了 .
#include<bits/stdc++.h>
using namespace std;
template<class T>void gi(T &x){
int f;char c;
for(f=1,c=getchar();c<'0'||c>'9';c=getchar())if(c=='-')f=-1;
for(x=0;c<='9'&&c>='0';c=getchar())x=x*10+(c&15);x*=f;
}
const int N=4e5+10,mod=998244353;
inline int qm(int x,int k){
int sum=1;
for(;k;k>>=1,x=1ll*x*x%mod)if(k&1)sum=1ll*sum*x%mod;
return sum;
}
int n,a[20][N],R[N],L=0;
inline int C(int n,int m){
if(n<m || n<0 || m<0)return 0;
int ret=1,I=1;
for(int i=1;i<=m;i++)ret=1ll*ret*(n-i+1)%mod,I=1ll*I*i%mod;
return 1ll*ret*qm(I,mod-2)%mod;
}
inline void NTT(int *A){
for(int i=0;i<n;i++)if(i<R[i])swap(A[i],A[R[i]]);
for(int i=1;i<n;i<<=1){
int t0=qm(3,(mod-1)/(i<<1)),x,y;
for(int j=0;j<n;j+=i<<1){
int t=1;
for(int k=0;k<i;k++,t=1ll*t*t0%mod){
x=A[j+k];y=1ll*A[j+k+i]*t%mod;
A[j+k]=(x+y)%mod;A[j+k+i]=(x-y+mod)%mod;
}
}
}
}
inline void mul(int *A,int *B){
NTT(A);NTT(B);
for(int i=0;i<n;i++)A[i]=1ll*A[i]*B[i]%mod;
NTT(A);reverse(A+1,A+n);
for(int i=0,t=qm(n,mod-2);i<n;i++)A[i]=1ll*A[i]*t%mod;
}
inline void solve(int l,int r,int d){
if(l==r){a[d][0]=l;a[d][1]=1;return ;}
int mid=(l+r)>>1,m=r-l+1;
solve(l,mid,d+1);
for(int i=0;i<=m;i++)a[d][i]=a[d+1][i];
solve(mid+1,r,d+1);
for(n=1,L=0;n<=m;n<<=1)L++;
for(int i=mid-l+2;i<n;i++)a[d][i]=0;
for(int i=r-mid+1;i<n;i++)a[d+1][i]=0;
for(int i=0;i<n;i++)R[i]=(R[i>>1]>>1)|((i&1)<<(L-1));
mul(a[d],a[d+1]);
}
int A,B;
int main(){
freopen("pp.in","r",stdin);
freopen("pp.out","w",stdout);
cin>>n>>A>>B;
if(n==1){
if(A+B-2>=0)puts("1");else puts("0");
exit(0);
}
solve(0,n-2,0);
cout<<1ll*a[0][A+B-2]*C(A+B-2,A-1)%mod;
return 0;
}
Codeforces 960G. Bandit Blues的更多相关文章
- Luogu P4609 [FJOI2016]建筑师&&CF 960G Bandit Blues
考虑转化题意,我们发现其实就是找一个长度为\(n\)的全排列,使得这个排列有\(A\)个前缀最大值,\(B\)个后缀最大值,求方案数 我们考虑把最大值拎出来单独考虑,同时定义一些数的顺序排列为单调块( ...
- 【CF960G】Bandit Blues(第一类斯特林数,FFT)
[CF960G]Bandit Blues(第一类斯特林数,FFT) 题面 洛谷 CF 求前缀最大值有\(a\)个,后缀最大值有\(b\)个的长度为\(n\)的排列个数. 题解 完完全全就是[FJOI] ...
- 【CF960G】Bandit Blues
[CF960G]Bandit Blues 题面 洛谷 题解 思路和这道题一模一样,这里仅仅阐述优化的方法. 看看答案是什么: \[ Ans=C(a+b-2,a-1)\centerdot s(n-1,a ...
- Divide by Zero 2018 and Codeforces Round #474 (Div. 1 + Div. 2, combined)G - Bandit Blues
题意:求满足条件的排列,1:从左往右会遇到a个比当前数大的数,(每次遇到更大的数会更换当前数)2.从右往左会遇到b个比当前数大的数. 题解:1-n的排列,n肯定是从左往右和从右往左的最后一个数. 考虑 ...
- CF960G Bandit Blues 第一类斯特林数+分治+FFT
题目传送门 https://codeforces.com/contest/960/problem/G 题解 首先整个排列的最大值一定是 \(A\) 个前缀最大值的最后一个,也是 \(B\) 个后缀最大 ...
- codeforces960G. Bandit Blues
题目链接:codeforces960G 来看看三倍经验:hdu4372 luogu4609 某蒟蒻的关于第一类斯特林数的一点理解QAQ:https://www.cnblogs.com/zhou2003 ...
- [CF960G] Bandit Blues
题意 给你三个正整数 \(n,a,b\),定义 \(A\) 为一个排列中是前缀最大值的数的个数,定义 \(B\) 为一个排列中是后缀最大值的数的个数,求长度为 \(n\) 的排列中满足 \(A = a ...
- CF960G Bandit Blues 第一类斯特林数、NTT、分治/倍增
传送门 弱化版:FJOI2016 建筑师 由上面一题得到我们需要求的是\(\begin{bmatrix} N - 1 \\ A + B - 2 \end{bmatrix} \times \binom ...
- Codeforces960G Bandit Blues 【斯特林数】【FFT】
题目大意: 求满足比之前的任何数小的有A个,比之后的任何数小的有B个的长度为n的排列个数. 题目分析: 首先写出递推式,设s(n,k)表示长度为n的排列,比之前的数小的数有k个. 我们假设新加入的数为 ...
随机推荐
- 用C#开发的双色球走势图(原创)值得园友拥有
首先声明,个人纯粹无聊之作,不作商业用途. 我相信每个人都拥有一个梦想那就是有朝一日能中500W,这个也一直是我的梦想,并默默每一期双色球或多或少要贡献自己一点点力量,本人并不属于那种铁杆的彩票迷,每 ...
- LeetCode138:Copy List with Random Pointer
题目: A linked list is given such that each node contains an additional random pointer which could poi ...
- SQL Server 错误:924 解决方法
USE master; GO DECLARE @SQL VARCHAR(MAX); SET @SQL='' SELECT @SQL=@SQL+'; KILL '+RTRIM(SPID) FROM ma ...
- C#计算机性能参数
Process proc = Process.GetCurrentProcess(); //string info = "内存:" + (Environment.WorkingSe ...
- UWP开发---嵌套DataTemplate&模板选择器
对于Json结构体items不完全一致的情况下,在UWP平台是如何处理数据,并通过不同的模板选择,进行显示呢? 一,嵌套Json分析 1,结构 通过抓取index的API(点击请求API)获取到的js ...
- 在QT中用git做版本管理时遇到的一些问题
1. 安装git sudo apt-get install git 2. 安装gitk sudo apt-get install gitk 要提交代码,点击 工具->git->local ...
- openstack 实用命令
port 1.创建port(create) i.随机ip openstack port create --network public --fixed-ip subnet=sub-public '' ...
- AGC032D Rotation Sort
题目传送门 Description 给定\(N\)的排列(\(N\leq5000\)),将任一区间最左侧的数插到该区间最右边的代价为\(A\),将任一区间最右侧的数插到该区间最左边的代价为\(B\), ...
- MySQL(视图、触发器、函数)
day61 参考:http://www.cnblogs.com/wupeiqi/articles/5713323.html 视图 视图:给某个查询语句设置别名,日后方便使用 ...
- Ubuntu 16.04LTS安装Nginx
Nginx ("engine x") 是一个高性能的 HTTP 和 反向代理 服务器,也是一个 IMAP/POP3/SMTP 代理服务器. Nginx 是由 Igor Sysoev ...