P1641 [SCOI2010] 生成字符串
点这里看题目
题意,n个1和m个0组成的串,1到任意位置的0个数小于等于1个数,求这样的串个数。
可以抽象为路径问题,从(0,0)走到(n,m),且不越过y=x的直线(在这条线下方),每次可以往上走或者往右走,分别对应方下一个0和放下一个1,
等同于 (0,0)到(n,m)的总路径数 减去 (-1,1)到(n,m)的总路径数。
即 C(n+m,n) - C(n+m,n+1)
#include<bits/stdc++.h>
using namespace std;
#define mod 20100403
#define maxn 1000005
#define LL long long
int n,m,fac[maxn*2],inv[maxn*2];
int C(int n,int m){
if (n<m) return 0;
return (LL)fac[n]*inv[m]%mod*inv[n-m]%mod;
}
int qsm(long long w,int b){
long long s=1;
for(;b;b>>=1){
if(b&1)s=s*w%mod;
w=w*w%mod;
}
return s;
}
int main(){
scanf("%d%d",&n,&m);
fac[0]=inv[0]=1;
for (int i=1;i<=n+m;++i) fac[i]=(LL)fac[i-1]*i%mod;
inv[n+m]=qsm(fac[n+m],mod-2);
for (int i=n+m-1;i>=1;i--) inv[i]=(LL)inv[i+1]*(i+1)%mod;
int ans=(C(n+m,m)-C(n+m,n+1)+mod)%mod;
printf("%d\n",ans);
return 0;
}