Achen毒瘤模拟赛T2——期望(mex)
题目大意:有m+1个白球排成一列,n次操作,每次前m个小球随机涂黑,求白球最小编号的期望值
PS:考试时候一眼望去(m+1)^n就直接输出了看来是我太菜了QWQ
做法:
很明显,我们一定要求出一个多项式:
容斥可得:
在交换一下求和顺序,得到:
线性筛可优化到O(m)。
#include<iostream> #include<cstdio> #include<cstring> #include<cmath> #include<algorithm> #include<set> #include<queue> #include<ctime> #define MAXN 200005 #define ll long long #define maxn 15 #define maxs 1000005 #define inf 1e9 #define eps 1e-9 #define mod 1000000007 using namespace std; inline char gc() { static char now[1<<16],*S,*T; if (T==S) { T=(S=now)+fread(now,1,1<<16,stdin); if (T==S) return EOF; } return *S++; } inline ll readlong() { ll x=0,f=1; char ch=getchar(); while(ch<'0'||ch>'9') { if(ch=='-')f=-1; ch=getchar(); } while(ch>='0'&&ch<='9') { x*=10; x+=ch-'0'; ch=getchar(); } return x*f; } inline int read() { int x=0,f=1; char ch=getchar(); while(ch<'0'||ch>'9') { if(ch=='-')f=-1; ch=getchar(); } while(ch>='0'&&ch<='9') { x*=10; x+=ch-'0'; ch=getchar(); } return x*f; } void putint(long long t) { int ans[40]= {0}; for(; t; t/=10)ans[++ans[0]]=t%10; for(; ans[0]; ans[0]--)putchar('0'+ans[ans[0]]); putchar('\n'); } const int N=1000005; ll ksm(ll x,ll k){ ll ret=1; ll ans=x%mod; while(k){ if(k&1){ ret=ret*ans%mod; } ans=ans*ans%mod; k>>=1; } return ret; } ll n,m; ll rev(ll x){ return ksm(x,mod-2); } ll fac[N]; ll cal(ll n,ll m){ // cout<<n<<' '<<m<<endl; if(n<m||n<0||m<0){ return 0; } // cout<<"*"; // cout<<fac[n]<<" "<<rev(1ll*fac[m]*fac[n-m]%mod)<<n ; return 1ll*fac[n]*rev(1ll*fac[m]*fac[n-m]%mod)%mod; } ll ans; int main(){ n=readlong(); m=readlong(); fac[0]=1; for(int i=1;i<=m+1;i++){ fac[i]=1ll*fac[i-1]*i%mod; } // cout<<"C:"<<cal(4,2)<<'\n'; // cout<<"x:"<<6*rev(2)%mod<<'\n'; // cout<<cal(667,91)<<'\n'; // system("pause"); int f; for(int i=0;i<=m;i++){ if(i&1){ f=-1; } else{ f=1; } ans=(ans+1ll*f*ksm(m-i,n)%mod*cal(m+1,i+1)%mod)%mod; // cout<<"ans="<<ans<<endl; } cout<<(ans+mod)%mod<<'\n'; return 0; }