[BZOJ 2729][HNOI2012]排队:高精度+组合数
2017-04-14 20:14
316 查看
点击这里查看原题
组合数问题,需要用到高精度。
把男生和老师混在一起,中间插入女生。两个老师刚好连在一起的情况为
A ( n+1 , n+1 ) * A ( 2 , 2 )
这种情况下两个老师间必须插入女生,于是将两个老师和一个女生捆绑在一起,情况为
m * A ( n+1 , n+1 ) * A ( 2 , 2 )
然后将剩余女生插入,情况为
A ( n+2 , m-1 )
两个老师不连在一起的情况为
A ( n+2 , n+2 ) - A ( n+1 , n+1 ) * A ( 2 , 2 )
直接插入女生的情况为
A ( n+3 , m )
于是,最终答案为
m * A ( n+1 , n+1 ) * A ( 2 , 2 ) * A ( n+2 , m-1 ) + A ( n+2 , n+2 ) - A ( n+1 , n+1 ) * A ( 2 , 2 ) * A ( n+3 , m )
高精度数组不能开太大,我最初开了5e4一直TLE。
组合数问题,需要用到高精度。
把男生和老师混在一起,中间插入女生。两个老师刚好连在一起的情况为
A ( n+1 , n+1 ) * A ( 2 , 2 )
这种情况下两个老师间必须插入女生,于是将两个老师和一个女生捆绑在一起,情况为
m * A ( n+1 , n+1 ) * A ( 2 , 2 )
然后将剩余女生插入,情况为
A ( n+2 , m-1 )
两个老师不连在一起的情况为
A ( n+2 , n+2 ) - A ( n+1 , n+1 ) * A ( 2 , 2 )
直接插入女生的情况为
A ( n+3 , m )
于是,最终答案为
m * A ( n+1 , n+1 ) * A ( 2 , 2 ) * A ( n+2 , m-1 ) + A ( n+2 , n+2 ) - A ( n+1 , n+1 ) * A ( 2 , 2 ) * A ( n+3 , m )
高精度数组不能开太大,我最初开了5e4一直TLE。
/* User:Small Language:C++ Problem No.:2729 */ #include<bits/stdc++.h> #define ll long long #define inf 999999999 using namespace std; int n,m; struct bignum{ int len,c[10005]; bignum(){ len=0; memset(c,0,sizeof(c)); } }x,y,z; bignum operator+(const bignum a,const bignum b){ bignum c; c.len=max(a.len,b.len); for(int i=1;i<=c.len;i++){ c.c[i]+=b.c[i]+a.c[i]; if(c.c[i]>=10000){ c.c[i+1]++; c.c[i]-=10000; } } if(c.c[c.len+1]) c.len++; return c; } bignum operator-(const bignum a,const bignum b){ bignum c; c.len=a.len; for(int i=1;i<=c.len;i++){ c.c[i]+=a.c[i]-b.c[i]; if(c.c[i]<0){ c.c[i+1]--; c.c[i]+=10000; } } while(c.c[c.len]==0) c.len--; return c; } bignum mul(bignum a,int b){ bignum c; if(b==0){ for(int i=1;i<=c.len;i++) c.c[i]=0; c.len=1; return c; } c.len=a.len; for(int i=1;i<=c.len;i++){ c.c[i]+=b*a.c[i]; c.c[i+1]+=c.c[i]/10000; c.c[i]%=10000; } while(c.c[c.len+1]) c.len++; return c; } void write(bignum p){ printf("%d",p.c[p.len]); for(int i=p.len-1;i;i--) printf("%04d",p.c[i]); printf("\n"); } int main(){ freopen("data.in","r",stdin);// scanf("%d%d",&n,&m); if(n+m==0||m>n+3){ printf("0\n"); return 0; } x.len=1; x.c[1]=1; y=z=x; x=mul(x,m); for(int i=2;i<=n+1;i++) x=mul(x,i); x=mul(x,2); for(int i=n+4-m;i<=n+2;i++) x=mul(x,i); for(int i=2;i<=n+2;i++) y=mul(y,i); for(int i=2;i<=n+1;i++) z=mul(z,i); z=mul(z,2); y=y-z; for(int i=n+4-m;i<=n+3;i++) y=mul(y,i); x=x+y; write(x); return 0; }
相关文章推荐
- 【BZOJ2729】【HNOI2012】排队 组合数 数论 Python高精度
- [BZOJ2729][HNOI2012]排队(组合数学+高精度)
- [BZOJ2729][HNOI2012]排队(组合数学+高精度)
- 组合数学+高精度 BZOJ2729 [HNOI2012]排队
- BZOJ2729 [HNOI2012]排队
- BZOJ 2729 HNOI2012 排队 组合数学
- BZOJ2729 [HNOI2012]排队
- [BZOJ2729] [HNOI2012]排队
- 2729:[HNOI2012]排队 - BZOJ
- bzoj2729 [HNOI2012]排队
- BZOJ2729 [HNOI2012]排队 【高精 + 组合数学】
- 【HNOI2012】【BZOJ2729】排队
- BZOJ 2729 [HNOI2012]排队
- 【BZOJ】2729: [HNOI2012]排队
- 排队 [HNOI 2012,Codevs 1994,Bzoj 2729]
- 【bzoj2729】[HNOI2012]排队 组合数学+高精度
- 【BZOJ】2729: [HNOI2012]排队
- 【BZOJ2729】[HNOI2012]排队 组合数
- bzoj2729: [HNOI2012]排队
- bzoj 2729: [HNOI2012]排队