HDU 5793

HDU 5793 - A Boring Question
题意:

  计算 ( ∑(0≤K1,K2...Km≤n )∏(1≤j<m) C[Kj, Kj+1]  ) % 1000000007=? (C[Kj, Kj+1] 为组合数)
    
分析:

  利用二项式展开: (a + b) ^ n =  ∑(r = 0, n) (C[n, r] * a^(n-r) * b^r )
    
    化简:
           ∑(0≤K1,K2...Km≤n )∏(1≤j<m) C[Kj, Kj+1]
    
         = ∑( Km = 0, n ) ∑( Km-1 = 0, Km ) ∑( Km-2 = 0, Km-1 )...∑( K1 = 0, K2 ) ( C[Km, Km-1] * C[Km-1, Km-2] *...*C[K2, K1]  )
           
         = ∑( Km = 0, n ) ∑( Km-1 = 0, Km )C[Km, Km-1]  ∑( Km-2 = 0, Km-1 )C[Km-1, Km-2] ... ∑( K2 = 0, K3 )C[K3, K2]  ∑( K1 = 0, K2)C[K2, K1]   //后面的积可分别提到和式前面
                                                                                                                                    
         = ∑( Km = 0, n ) ∑( Km-1 = 0, Km )C[Km, Km-1]  ∑( Km-2 = 0, Km-1 )C[Km-1, Km-2] ... ∑( K2 = 0, K3 ) ( C[K3, K2] * 2^K2 )  

                                                           // ∑( K1 = 0, K2)C[K2, K1]  为(1 + 1) ^ k2 的二项式展开
                                                                                                                                    
         = ∑( Km = 0, n ) m ^ Km          //∑( K2 = 0, K3 ) ( C[K3, K2] * 2^K2 ) 为 (1 + 2) ^ k3 的二项式展开 ,接下来依次向上化简
         
         = ( m^(n+1) - 1 ) / ( m - 1 )   //等比数列求和公式
         
    接下来求快速幂和逆元即可.

  (博客园怎么连个公式编辑器都没有= =)

 1 #include <iostream>
 2 #include <cstdio>
 3 using namespace std;
 4 #define LL long long
 5 const LL MOD = 1000000007;
 6 LL PowMod(LL a, LL p, LL MOD)
 7 {
 8     int res = 1;
 9     while(p)
10     {
11         if(p&1) res = (res * a) %MOD;
12         p >>= 1;
13         a = (a * a) % MOD;
14     }
15     return res;
16 }
17 int t;
18 LL n,m;
19 int main()
20 {
21     scanf("%d",&t);
22     while(t--)
23     {
24         scanf("%lld%lld", &n, &m);
25         LL ans = PowMod(m, n+1, MOD);
26         --ans;
27         LL inv = PowMod(m-1, MOD-2, MOD);
28         ans = (ans * inv) % MOD;
29         printf("%lld
",ans);
30     }
31 } 
我自倾杯,君且随意
原文地址:https://www.cnblogs.com/nicetomeetu/p/5741774.html