题目

我们发现我们得正难则反

还是设\(f_i\)表示长度为\(i\)的序列个数

考虑容斥

\[f_i=i!-\sum_{j=1}^{i-1}f_j(i-j)!
\]

\(i!\)显然是总方案数,我们减掉不合法的方案数,显然\(1\)到\(j\)这些数强行合法,之后\(j+1\)到\(i\)在后面自由排列,由于在\(j\)后面这个位置没有一个数比之前的小,所以一定不合法,同时通过首次不合法的位置区分开不同的序列,从而做到不重不漏

但是上面有一个小问题就是\(f_0=0\),但是按照上面的递推数列来推会造成\(f_0=1\)

于是应该写成

\[f_i=i!-\sum_{j=1}^{i-1}f_j(i-j)!-[i=0]
\]

也就是

\[\sum_{j=1}^if_j(i-j)!=i!-[i=0]
\]

设阶乘的生成函数是\(G(x)\)

就有

\[F(x)\times G(x)=G(x)-1
\]

\[F(x)=\frac{G(x)-1}{G(x)}=1-\frac{1}{G(x)}
\]

也就是对阶乘求一个逆

代码

#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
#define re register
#define LL long long
#define max(a,b) ((a)>(b)?(a):(b))
#define min(a,b) ((a)<(b)?(a):(b))
const int maxn=261244+1005;
inline int read() {
char c=getchar();int x=0;while(c<'0'||c>'9') c=getchar();
while(c>='0'&&c<='9') x=(x<<3)+(x<<1)+c-48,c=getchar();return x;
}
const LL G[2]={3,332748118};
const LL mod=998244353;
LL fac[maxn],K[maxn],D[maxn],C[maxn],A[maxn],B[maxn];
int n,rev[maxn],ask[maxn],len,T;
inline LL ksm(LL a,LL b) {LL S=1;while(b) {if(b&1) S=S*a%mod;b>>=1;a=a*a%mod;}return S;}
inline void NTT(LL *f,int o) {
for(re int i=0;i<len;i++) if(i<rev[i]) std::swap(f[i],f[rev[i]]);
for(re int i=2;i<=len;i<<=1) {
int ln=i>>1;LL og1=ksm(G[o],(mod-1)/i);
for(re int l=0;l<len;l+=i) {
LL t,og=1;
for(re int x=l;x<l+ln;x++) {
t=(og*f[ln+x])%mod;
f[ln+x]=(f[x]-t+mod)%mod;
f[x]=(f[x]+t)%mod;
og=(og*og1)%mod;
}
}
}
if(!o) return;
LL inv=ksm(len,mod-2);
for(re int i=0;i<len;i++) f[i]=(f[i]*inv)%mod;
}
inline void mul(int n,LL *A,LL *B) {
len=1;while(len<n+n) len<<=1;
for(re int i=0;i<len;i++) rev[i]=rev[i>>1]>>1|((i&1)?len>>1:0);
NTT(A,0),NTT(B,0);for(re int i=0;i<len;i++) A[i]=(A[i]*B[i])%mod;
NTT(A,1);for(re int i=n;i<len;i++) A[i]=0;
}
inline void Inv(int n,LL *A,LL *B) {
if(n==1) {B[0]=ksm(A[0],mod-2);return;}
Inv((n+1)>>1,A,B);
memset(C,0,sizeof(C));memset(D,0,sizeof(D));memset(K,0,sizeof(K));
for(re int i=0;i<n;i++) C[i]=K[i]=B[i],D[i]=A[i];
mul(n,C,K);mul(n,C,D);
for(re int i=0;i<n;i++) B[i]=(2ll*B[i]-C[i]+mod)%mod;
}
int main() {
T=read();
for(re int i=1;i<=T;i++)
ask[i]=read(),n=max(n,ask[i]+1);
A[0]=1;for(re int i=1;i<n;i++) A[i]=(A[i-1]*1ll*i)%mod;
Inv(n,A,B);
for(re int i=0;i<n;i++) B[i]=(mod-B[i])%mod;B[0]++;
for(re int i=1;i<=T;i++) printf("%lld\n",B[ask[i]]);
return 0;
}

【51nod 1514】 美妙的序列的更多相关文章

  1. 51nod 1514 美妙的序列

    Description 长度为n的排列,且满足从中间任意位置划分为两个非空数列后,左边的最大值>右边的最小值.问这样的排列有多少个%998244353 题面 Solution 正难则反 \(f[ ...

  2. 51nod 1514 美妙的序列 分治NTT + 容斥

    Code: #include<bits/stdc++.h> #define ll long long #define mod 998244353 #define maxn 400000 # ...

  3. NTT【51nod】1514 美妙的序列

    题意:1~n 的全排列中,有多少个排列满足任意从中间切成两段后,左边段的最大值大于右边段的最小值? 例如:n为3时有3种 2 3 1 3 1 2 3 2 1 解释:比如 2 3 1 (2) (3 1) ...

  4. Solution -「51nod 1514」美妙的序列

    \(\mathcal{Description}\)   Link.   称排列 \(\{p_n\}\) 美妙,当且仅当 \((\forall i\in[1,n))(\max_{j\in[1,i]}\{ ...

  5. [51nod1514] 美妙的序列

    Description 如果对于一个 \(1\sim n\) 的排列满足: 在 \(1\sim n-1\) 这些位置之后将序列断开,使得总可以从右边找一个数,使得该数不会比左边所有数都大,则称该序列是 ...

  6. 51nod 1510 最小化序列 | DP 贪心

    题目描述 现在有一个长度为n的数组A,另外还有一个整数k.数组下标从1开始. 现在你需要把数组的顺序重新排列一下使得下面这个的式子的值尽可能小. ∑|A[i]−A[i+k]| 特别的,你也可以不对数组 ...

  7. 【51nod】1251 Fox序列的数量

    题解 容斥题 我们枚举出现次数最多的数出现了K次 然后我们需要计算的序列是所有数字出现个数都不超过K - 1次 我们枚举不合法的数字的数目j,说明这个排列里除了我们固定出现K次的数至少有j个数是不合法 ...

  8. 【51nod 1251】 Fox序列的数量(以及带限制插板法讲解)

    为什么网上没有篇详细的题解[雾 可能各位聚聚觉得这道题太简单了吧 /kk 题意 首先题目是求满足条件的序列个数,条件为:出现次数最多的数仅有一个 分析 感谢 刚睡醒的 JZ姐姐在咱写题解忽然陷入自闭的 ...

  9. 【51NOD 1478】括号序列的最长合法子段

    很恶心啊,一道水题改了半天,主要是各种细节没有注意到,包括左括号剩余时有可能会出错的情况,需要从后往前扫 贡献一组测试数据: ((()))())(())(( 答案:8 1 #include<cs ...

随机推荐

  1. HTTP协议状态码学习

    一直以来都在追求实战,从而忽视了对理论知识的深入学习和理解.这并不可怕,可怕的是当意识到自己的不足时,没有行动. 1xx(临时响应) 表示临时响应并需要请求者继续执行操作的状态代码. 代码   说明 ...

  2. 在 Azure Web 应用中创建 .NET 应用程序

    本快速入门帮助你在数分钟内将你的第一个 ASP.NET Web 应用部署到 Azure 应用服务.完成本教程后,你将能够在云中启动并运行一个简单的 Web 应用.在本教程中完成的所有操作均符合1 元试 ...

  3. distinct 用法

    参考 1.作用于单列 2.作用于多列 3.COUNT统计 4.distinct必须放在开头 5.其他 在表中,可能会包含重复值.这并不成问题,不过,有时您也许希望仅仅列出不同(distinct)的值. ...

  4. PoPo数据可视化周刊第2期

    羡辙在bilibili开课啦 就在这个月,不知道是不是受了 @Jannchie见齐 的影响,羡辙竟然在bilibili开授Echarts课程,目前已开课两节. [滚城一团]的 ECharts 训练营 ...

  5. Vijos / 题库 / 输油管道问题

    背景 想念car的GF,car就出了道水题! 描述 某石油公司计划建造一条由东向西的主输油管道.该管道要穿过一个有n 口油井的油田.从每口油井都要有一条输油管道沿最短路经(或南或北)与主管道相连.如果 ...

  6. 手机浏览器的User-Agent汇总

    手机浏览器的User-Agent汇总 之前介绍的 更简洁的方式修改Chrome的User Agent,轻松体验移动版网络这种简洁的方法好像只适用于Chrome, Chrome不只是浏览界面简洁,对应的 ...

  7. ubuntu下面解压tar.gz包报错:tar命令报错: gzip: stdin: not in gzip format tar: Child returned status 1 tar: Error

    原因: 压缩包文件不完整(损坏或者其他原因) 比如今天下载的tomcat8,使用ubuntu的命令下载的 curl -O http://apache.mirrors.ionfish.org/tomca ...

  8. 检查 NaN 数据值 (C/C++/Python 实现)

    NaN 是 Not a Number 的缩写.它是一个数值类型值,通常在浮点计算中,表示未定义或无法表示的值.而且,不能直接使用相等运算符 (==) 检查 NaN.由于在程序中,nan == nan ...

  9. C# WinForm窗体及其控件自适应各种屏幕分辨率

    C# WinForm窗体及其控件自适应各种屏幕分辨率 一.说明  我们自己编写程序的界面,会遇到各种屏幕分辨率,只有自适应才能显的美观.实际上,做到这点也很简单,就是首先记录窗体和它上面控件的初始位置 ...

  10. C# winfrom界面跳转闪烁问题解决方法

    在窗体的构造函数中添加代码: SetStyle(ControlStyles.UserPaint, true); SetStyle(ControlStyles.AllPaintingInWmPaint, ...