Description

如果对于一个 \(1\sim n\) 的排列满足:

在 \(1\sim n-1\) 这些位置之后将序列断开,使得总可以从右边找一个数,使得该数不会比左边所有数都大,则称该序列是“美妙的”。

给出 \(n\) ,求出长度为 \(n\) 的美妙的序列的数量。多组数据。 \(T,n\leq 10^5\)。对 \(998244353\) 取模。

Solution

暴力DP是 \(O(Tn^2)\) 的。我们需要发现题目的隐藏性质。

如果某个排列不是美妙的,那一定存在一个位置 \(k\) ,使得 \(k\) 右边的最小值大于左边的最大值。也就是说,\(k\) 左边是一个 \(1\sim k\) 的排列。

问题就转化成了求有多少长度为 \(n\) 的排列,使得任意一个前缀都不是 \(1\sim k\) 的排列。

考虑 \(DP\) 。设 \(f[i]\) 表示长度为 \(i\) 的美妙的排列个数。有转移:
\[ f[n]=n!-\sum_{i=1}^{n-1}i!\cdot f[n-i]\quad f[0]=0 \]
这个转移的含义是用总方案数减去不合法的方案数,也就是减去所有不美妙的排列。于是枚举最靠右不能满足要求的位置,然后把序列划分成两端。前一段是一个 \(1\sim k\) 的排列,后一段一定是一个美妙的序列(不然一定可以找到一个更靠右的不满足题意的位置)。

这时候就可以分治FFT了。但是别着急,一般分治FFT能做的多项式求逆都可以做。再推几步式子:
\[ f[n]=n!-\sum_{i=1}^n i!\cdot f[n-i] \]
移项:
\[ \sum_{i=0}^n i!\cdot f[n-i]=n! \]
由于有 \(f[0]=0\) 的特殊情况所以需要特殊考虑:
\[ \text{当n=0时}\quad \sum_{i=0}^n i!\cdot f[n-i]+1=n! \]
于是令 \(F\) 为 \(f\) 的生成函数,\(G=\sum\limits_{i=0}^\infty i!\cdot x^i\),于是就有 \(F\times G+1=G\),移项可以得到:
\[ F=1-\frac1{G} \]
多项式求逆即可。复杂度 \(O(n\log n)\)。

Code

#pragma GCC optimize(2)
#include<bits/stdc++.h>
using std::min;
using std::max;
using std::swap;
using std::vector;
typedef double db;
typedef long long ll;
#define pb(A) push_back(A)
#define pii std::pair<int,int>
#define all(A) A.begin(),A.end()
#define mp(A,B) std::make_pair(A,B)
#define int long long
const int n=1e5;
const int N=4e5+5;
const int mod=998244353;int fac[N];
int tmpa[N];
int b[N],c[N];
int lim,rev[N];int getint(){int X=0,w=0;char ch=getchar();while(!isdigit(ch))w|=ch=='-',ch=getchar();while( isdigit(ch))X=X*10+ch-48,ch=getchar();if(w) return -X;return X;
}int ksm(int a,int b=mod-2,int ans=1){while(b){if(b&1) ans=ans*a%mod;a=a*a%mod;b>>=1;} return ans;
}void ntt(int *f,int opt){for(int i=1;i<lim;i++) if(i<rev[i]) swap(f[i],f[rev[i]]);for(int mid=1;mid<lim;mid<<=1){int tmp=ksm(3,(mod-1)/(mid<<1));if(opt<0) tmp=ksm(tmp);for(int R=mid<<1,j=0;j<lim;j+=R){int w=1;for(int k=0;k<mid;k++,w=w*tmp%mod){int x=f[j+k],y=w*f[j+k+mid]%mod;f[j+k]=(x+y)%mod,f[j+k+mid]=(mod+x-y)%mod;}}} if(opt<0)for(int in=ksm(lim),i=0;i<lim;i++) f[i]=f[i]*in%mod;
}void solveinv(int len,int *a,int *b){if(!len) return b[0]=ksm(a[0]),void();solveinv(len>>1,a,b);lim=len+len;for(int i=1;i<lim;i++) rev[i]=(rev[i>>1]>>1)|(i&1?lim>>1:0);for(int i=0;i<len;i++) tmpa[i]=a[i];ntt(tmpa,1),ntt(b,1);for(int i=0;i<lim;i++) b[i]=b[i]*(2ll-tmpa[i]*b[i]%mod+mod)%mod;ntt(b,-1);for(int i=len;i<lim;i++) b[i]=0;for(int i=0;i<lim;i++) tmpa[i]=0;
}signed main(){fac[0]=1;for(int i=1;i<=n;i++) fac[i]=fac[i-1]*i%mod;solveinv(131072,fac,b);for(int i=1;i<=n;i++) b[i]=mod-b[i];int T=getint();while(T--){int x=getint();printf("%lld\n",b[x]);} return 0;
}

转载于:https://www.cnblogs.com/YoungNeal/p/10275637.html

[51nod1514] 美妙的序列相关推荐

  1. 2017西安交大ACM小学期 美妙音乐[差分KMP匹配]

    美妙音乐 发布时间: 2017年7月3日 13:14   最后更新: 2017年7月5日 13:47   时间限制: 500ms   内存限制: 128M 描述 一段音乐是由若干个音符组成的,音乐中的 ...

  2. 序列周期性与魔术(六)——魔术欣赏与解析续集

    不知不觉写到第6篇了,这也是本系列的收官之作,从数学到魔术的美妙旅程,就此即将告一段落.往期精彩回顾: 序列周期性与魔术(五)--魔术欣赏与解析 序列周期性与魔术(四)--周期序列数学性质深入探秘 序 ...

  3. 判断某数组是不是二叉树的前序遍历序列 python递归

    code class Solution:def VerifySquenceOfBST(self, sequence):# write code hereif len(sequence) <= 0 ...

  4. pytorch中如何处理RNN输入变长序列padding

    一.为什么RNN需要处理变长输入 假设我们有情感分析的例子,对每句话进行一个感情级别的分类,主体流程大概是下图所示: 思路比较简单,但是当我们进行batch个训练数据一起计算的时候,我们会遇到多个训练 ...

  5. PyTorch: 序列到序列模型(Seq2Seq)实现机器翻译实战

    版权声明:博客文章都是作者辛苦整理的,转载请注明出处,谢谢!http://blog.csdn.net/m0_37306360/article/details/79318644 简介 在这个项目中,我们 ...

  6. 支持向量机SVM序列最小优化算法SMO

    支持向量机(Support Vector Machine)由V.N. Vapnik,A.Y. Chervonenkis,C. Cortes 等在1964年提出.序列最小优化算法(Sequential ...

  7. LeetCode简单题之最长特殊序列 Ⅰ

    题目 给你两个字符串 a 和 b,请返回 这两个字符串中 最长的特殊序列 .如果不存在,则返回 -1 . 「最长特殊序列」 定义如下:该序列为 某字符串独有的最长子序列(即不能是其他字符串的子序列) ...

  8. GStreamer 1.0 series序列示例

    GStreamer 1.0 series序列示例 OpenEmbedded layer for GStreamer 1.0 这layer层为GStreamer 1.0框架提供了非官方的支持,用于Ope ...

  9. 微调BERT:序列级和令牌级应用程序

    微调BERT:序列级和令牌级应用程序 Fine-Tuning BERT for Sequence-Level and Token-Level Applications 为自然语言处理应用程序设计了不同 ...

  10. 【剑指Offer】23、二叉搜索树的后序遍历序列

      题目描述:   输入一个整数数组,判断该数组是不是某二叉搜索树的后序遍历的结果.如果是则输出Yes,否则输出No.假设输入的数组的任意两个数字都互不相同.   解题思路:   对于后续遍历序列,序 ...

最新文章

  1. 动态语言的灵活性是把双刃剑 -- 以Python语言为例
  2. 【Live555】live555源码详解(九):ServerMediaSession、ServerMediaSubsession、live555MediaServer
  3. lede 命令 启用 ssh_PHP imap_open函数任意命令执行漏洞
  4. 洛谷.4172.[WC2006]水管局长(LCT Kruskal)
  5. GridView相关问题汇总
  6. Java 常用语法和数据结构
  7. LINQ分组查询统计
  8. tcpclient java_[Java] 网络-01 TCPClient / TCPServer
  9. 6-2 递归方法:汉诺塔问题 (10 分)
  10. 通过Python给头像加国旗,10多行代码搞定,就别@官方了
  11. RuntimeError: mat1 dim 1 must match mat2 dim 0
  12. 苹果蕉文案:水果店苹果蕉推广文案
  13. c语言西南交通大学出版社答案,西南交通大学C++上机实验答案
  14. matlab求基音频率,语音中提取基音频率matlab程序.doc
  15. MySQL单表查询总结
  16. 手机巨头关注的5G,可不仅仅是5G网络那么简单!
  17. 矩阵实验:图形图像处理
  18. 库存融资管理系统-覆盖全行业几十种第三方接口
  19. 自定义线程池拒绝策略
  20. 银行类 售前培训 知识 总结

热门文章

  1. Fedora 25-64位操作系统中安装配置Hyperledger Fabric过程
  2. 数据库死锁,导致CPU异常增长
  3. StringIndexOutOfBoundsException
  4. Java IO1:IO和File
  5. offsetTop和scrollTop差异
  6. iOS 更改导航栏返回button文字
  7. Alfresco安装与配置图解
  8. 让人等不及的潮州小吃“来不及”
  9. GridView中设置DataFormatString无效的解决方法.
  10. 论文阅读笔记——拥塞控制算法PCC