/******************************
大组合取模之:1<=n<=m<=1e6,1<=p<=1e9
使用:程序最开始调用getprime(),需要时调用C(n,m,p)
复杂度:O( n*log(n) )
******************************/
typedef long long ll;
#define N 210000
int PRIME[N/2];
void getprime()
{
bool pmark[N+1000];
memset(pmark,0,sizeof(pmark));
int pcnt=0;
PRIME[pcnt++]=2;
for(int i=3;i<N+1000;i+=2)
{
if(pmark[i]==0)
{
PRIME[pcnt++]=i;
for(int j=i;j<N+1000;j+=i) pmark[j]=1;
}
}
}
/**************
快速幂模板
调用:Quk_Mul(a,b,mod)
返回:a^b%mod
复杂度:当mod>10^9,log(mod)*log(b),否则log(b)
***************/
long long Mod_Mul(long long a,long long b,long long mod)
{
long long msum=0;
while(b)
{
if(b&1) msum = (msum+a)%mod;
b>>=1;
a = (a+a)%mod;
}
return msum;
}
long long Quk_Mul(long long a,long long b,long long mod)
{
bool qmflag=mod>1e9?1:0;
long long qsum=1;
while(b)
{
if(b&1) qsum = (qmflag==1) ? Mod_Mul(qsum,a,mod) : (qsum*a)%mod;
b>>=1;
a = (qmflag==1) ? Mod_Mul(a,a,mod) : (a*a)%mod;
}
return qsum;
}
// 得到n! 中有多少个d因子
int getdn(int n,int d)
{
int sum=0;
while(n)
{
sum += n/d;
n/=d;
}
return sum;
}
ll C(int n,int m,ll p)
{
if(m>n) return 0;
ll sumc=1;
for(int i=0;PRIME[i]<=n;i++)
{
int cnum = getdn(n,PRIME[i])-getdn(m,PRIME[i])-getdn(n-m,PRIME[i]);
sumc = sumc*Quk_Mul(PRIME[i], cnum, p)%p;
}
return sumc;
}
/*
int main() {
getprime();
int T;
cin>>T;
while(T--)
{
int n,m,p;
cin>>n>>m>>p;
cout<<C(n,m,p)<<endl;
}
return 0;
}
*/