zoukankan      html  css  js  c++  java
  • 【HDU 1133】 Buy the Ticket (卡特兰数)

    (卡特兰数)hdu1133 <wbr> <wbr>Buy <wbr>the <wbr>Ticket
    (卡特兰数)hdu1133 <wbr> <wbr>Buy <wbr>the <wbr>Ticket

    【分析】

      

      当m<n,显然一定不合法。

      所以我们考虑m>=n,类比n=m时的方案数推法,总方案为C(m,m+n),要减去不符合的情况。

      我们扫描一个数,找到第一个不符合的位置,假设是有a个1,a+1个1,那么我们后面会填n-a-1个-1,m-a个1,我们把后面的1和-1交换,就得到了一个有m-a个-1,n-a-1个1的数,方案为C(m+1,m+n),把它减掉即可,

      即ans=C(m,m+n)-C(m+1,m+n)。因为每个人不相同最后1还要乘n!*m!。
      为什么要用1和-1互换呢,

      首先对于一个不合法串是唯一对应一个转换串的(就按照上述方法转换),

      然后对于一个转换串是一定对应一个不合法串的,方法是找到其第一个不合法的地方,然后后面部分-1和1转换。

      还有就是转换串一定不合法,因为它有m+1个-1,n-1个1,而m>=n。这就是他比原串优越的地方,用他可以完全取代不合法串!

    代码如下:(还没有测,hdu挂掉了)

     1 #include<cstdio>
     2 #include<cstdlib>
     3 #include<cstring>
     4 #include<iostream>
     5 #include<algorithm>
     6 #include<queue>
     7 #include<cmath>
     8 using namespace std;
     9 #define Maxn 110
    10 
    11 struct node
    12 {
    13     int d[Maxn],ln;
    14 };
    15 node t[3];
    16 
    17 void mul(int x,int y)
    18 {
    19     int add=0;
    20     for(int i=1;i<=t[x].ln;i++)
    21     {
    22         t[x].d[i]*=y;
    23         t[x].d[i]+=add;
    24         add=t[x].d[i]/10;
    25         t[x].d[i]%=10;
    26         // if(i==t[x].ln&&t[x].d[i+1]!=0) t[x].ln++;
    27     }
    28     t[x].d[t[x].ln+1]=add;
    29     while(t[x].d[t[x].ln+1]!=0)
    30     {
    31         t[x].ln++;
    32         t[x].d[t[x].ln+1]=t[x].d[t[x].ln]/10;
    33         t[x].d[t[x].ln]%=10;
    34     }
    35 }
    36 
    37 void get_ans()
    38 {
    39     t[2].ln=t[0].ln;
    40     for(int i=1;i<=t[0].ln;i++)
    41     {
    42         if(t[0].d[i]<t[1].d[i])
    43         {
    44             t[0].d[i+1]--;
    45             t[0].d[i]+=10;
    46         }
    47         t[2].d[i]=t[0].d[i]-t[1].d[i];
    48     }
    49     while(t[2].d[t[2].ln]==0) t[2].ln--;
    50     if(t[2].ln==0) t[2].ln++;
    51 }
    52 
    53 int main()
    54 {
    55     int kase=0;
    56     while(1)
    57     {
    58         int m,n;
    59         scanf("%d%d",&m,&n);
    60         if(m==0&&n==0) break;
    61         printf("Test #%d:
    ",++kase);
    62         if(m<n) {printf("0
    ");continue;}
    63         memset(t[0].d,0,sizeof(t[0].d));
    64         memset(t[1].d,0,sizeof(t[1].d));
    65         t[0].d[1]=1; t[0].ln=1;
    66         for(int i=1;i<=m+n;i++)
    67         {
    68             mul(0,i);
    69         }
    70         t[1].d[1]=1; t[1].ln=1;
    71         for(int i=1;i<=m;i++)
    72         {
    73             mul(1,i);
    74         }
    75         for(int i=m+2;i<=m+n;i++)
    76         {
    77             mul(1,i);
    78         }
    79         mul(1,n);
    80         get_ans();
    81         for(int i=t[2].ln;i>=1;i--) printf("%d",t[2].d[i]);
    82         printf("
    ");
    83     }
    84     return 0;
    85 }
    [HDU 1133]

    2016-09-07 22:06:16

  • 相关阅读:
    SpringBoot中添加事务
    隐藏样式
    Mybatis配置解析
    题目1064:反序数------玩转小聪明
    题目1063:整数和
    题目1062:分段函数23333333333333
    题目1060:完数VS盈数------这题做得我想骂人
    题目1059:abc----------就喜欢这样的题
    题目1050:完数-----------runtime error的问题
    题目1049:字符串去特定字符
  • 原文地址:https://www.cnblogs.com/Konjakmoyu/p/5851273.html
Copyright © 2011-2022 走看看