「BZOJ3398」[Usaco2009 Feb] Bullcow 牡牛和牝牛
Description
约翰要带N(1≤N≤100000)只牛去参加集会里的展示活动,这些牛可以是牡牛,也可以是牝牛.牛们要站成一排.但是牡牛是好斗的,为了避免牡牛闹出乱子,约翰决定任意两只牡牛之间至少要有K(O≤K<N)只牝牛.
请计算一共有多少种排队的方法.所有牡牛可以看成是相同的,所有牝牛也一样.
Input
一行,输入两个整数N和K.
Output
一个整数,表示排队的方法数.
Sample Input
4 2
Sample Output
6
样例说明
6种方法分别是:牝牝牝牝,牡牝牝牝,牝牡牝牝,牝牝牡牝,牝牝牝牡,牡牝牝牡
样例说明
6种方法分别是:牝牝牝牝,牡牝牝牝,牝牡牝牝,牝牝牡牝,牝牝牝牡,牡牝牝牡
题解
我用了逗比的排列组合。。。
意会一下。。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 |
#include<iostream> #include<cstdio> #include<cstring> #include<vector> #include<algorithm> #define mod 5000011 #define ll long long using namespace std; inline int read() { int x=0;char ch=getchar(); while(ch<'0'||ch>'9')ch=getchar(); while(ch>='0'&&ch<='9'){x=x*10+ch-'0';ch=getchar();} return x; } int n,K,ans; ll qpow(ll a,int b) { ll sum=1; for(int i=b;i;i>>=1,a=(a*a)%mod) if(i&1)sum=(sum*a)%mod; return sum; } ll C(int n,int m) { if(m>n-m)m=n-m; ll s1=1,s2=1; for(int i=1;i<=m;i++)s1=s1*(n-i+1)%mod; for(int i=1;i<=m;i++)s2=(s2*i)%mod; return s1*qpow(s2,mod-2)%mod; } int main() { n=read();K=read(); ans=1; for(int i=1;i<=n;i++) { int t=n-(i-1)*K; if(t<i)break; ans=(ans+C(t,i))%mod; } printf("%d\n",ans); return 0; } |
Subscribe