CF285E题解

果然数数题比什么阴间巨大多细节哈希点分治简单多了

恰好太难了,考虑容斥,考虑钦定 m 个位置满足 |ipi|=1

很明显有 f(m)=i=mn(im)g(i),二项式反演一下就有 g(m)=i=mn(im)(1)imf(i)

dp[n][m][0/1][0/1] 表示前 n 个位置中共有 m 个满足 |ipi|=1 的且仅考虑这一部分对答案贡献的方案数,且是/否存在 j 满足 pj=n1pj=n。那么有 f(m)=dp[n][m][0/1][0/1]×(nm)!

这个比较好转移。复杂度 O(n2)

鹰角你什么时候送我们六星自选卷啊

提交记录

好吧代码在这里

#include<iostream>
const int M=1005,mod=1e9+7;
int n,m,F[M],inv[M],fac[M],X[2][2][M],Y[2][2][M],*f[2][2],*g[2][2];
inline int Add(const int&a,const int&b){
	return a+b>=mod?a+b-mod:a+b;
}
signed main(){
	int ans(0);std::cin>>n>>m;for(int i=0;i^2;++i)for(int j=0;j^2;++j)f[i][j]=X[i][j],g[i][j]=Y[i][j];
	f[0][0][0]=1;f[0][1][1]=1;inv[1]=fac[0]=fac[1]=1;for(int i=2;i<=n;++i)inv[i]=1ll*(mod-mod/i)*inv[mod%i]%mod;
	for(int i=2;i<=n;++i)fac[i]=1ll*fac[i-1]*i%mod;
	for(int i=2;i<=n;++i){
		for(int k=1;k<=i;++k){
			g[0][0][k]=Add(Add(f[0][0][k],f[1][0][k]),f[0][0][k-1]);g[0][1][k]=Add(f[0][0][k-1],f[1][0][k-1]);
			g[1][0][k]=Add(Add(f[0][1][k],f[1][1][k]),f[0][1][k-1]);g[1][1][k]=Add(f[0][1][k-1],f[1][1][k-1]);
		}
		g[0][0][0]=1;for(int i=0;i^2;++i)for(int j=0;j^2;++j)std::swap(f[i][j],g[i][j]);
	}
	for(int i=0;i<=n;++i)F[i]=1ll*Add(f[0][0][i],f[1][0][i])*fac[n-i]%mod;
	for(int C(1),i=m;i<=n;++i,C=1ll*i*inv[i-m]%mod*C%mod)ans=(ans+1ll*C*(i-m&1?mod-F[i]:F[i]))%mod;std::cout<<ans;
}

本文作者:Prean

本文链接:https://www.cnblogs.com/lmpp/p/16525026.html

版权声明:本作品采用知识共享署名-非商业性使用-禁止演绎 2.5 中国大陆许可协议进行许可。

posted @   Prean  阅读(22)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· TypeScript + Deepseek 打造卜卦网站:技术与玄学的结合
· Manus的开源复刻OpenManus初探
· 三行代码完成国际化适配,妙~啊~
· .NET Core 中如何实现缓存的预热?
· 如何调用 DeepSeek 的自然语言处理 API 接口并集成到在线客服系统
var canShowAdsense=function(){return !!0};
点击右上角即可分享
微信分享提示
评论
收藏
关注
推荐
深色
回顶
收起