• lightoj 1102


    1102 - Problem Makes Problem

    As I am fond of making easier problems, I discovered a problem. Actually, the problem is 'how can you make n by adding k non-negative integers?' I think a small example will make things clear. Suppose n=4and k=3. There are 15 solutions. They are

    1.      0 0 4

    2.      0 1 3

    3.      0 2 2

    4.      0 3 1

    5.      0 4 0

    6.      1 0 3

    7.      1 1 2

    8.      1 2 1

    9.      1 3 0

    10.  2 0 2

    11.  2 1 1

    12.  2 2 0

    13.  3 0 1

    14.  3 1 0

    15.  4 0 0

    As I have already told you that I use to make problems easier, so, you don't have to find the actual result. You should report the result modulo 1000,000,007.

    Input

    Input starts with an integer T (≤ 25000), denoting the number of test cases.

    Each case contains two integer n (0 ≤ n ≤ 106) and k (1 ≤ k ≤ 106).

    Output

    For each case, print the case number and the result modulo 1000000007.

    Sample Input

    Output for Sample Input

    4

    4 3

    3 5

    1000 3

    1000 5

    Case 1: 15

    Case 2: 35

    Case 3: 501501

    Case 4: 84793457


    PROBLEM SETTER: JANE ALAM JAN

    http://www2.chinaedu.com/101resource004/wenjianku/200501/101ktb/lanmu/XF1S0213/XF1S0213.htm

    隔板法

    思路:组合数学,费马小定理求逆元,快速幂。

    用隔板法来求,这个问题可以转化为x1+x2+...xk=n的多元方不同程解的个数,并且xk〉=0;

    就是组合数C(n+k-1,k-1) ,那么由费马小定理ap-1==1mod(p);设a-1为a的逆元则(a*a-1*ap-2)=a-1mod(p);

    即ap-2=a-1mod(p);C(a,b) =(f(a))/(f(b)*f(a-b));

    C(a,b)%p=((f(a))/(f(b)*f(a-b)))%P;其中f(n)表示阶乘。

    (a/b)%p=k%p;两边同乘b ----a%p=(k*b)%p;然后两边同乘b-1%p;----a*b-1%p=k%p;

    而根据费马小定理ap-2=a-1mod(p);用快速幂求下bp-2%p就可以了。

     1 #include<stdio.h>
     2 #include<algorithm>
     3 #include<iostream>
     4 #include<string.h>
     5 #include<math.h>
     6 #include<queue>
     7 using namespace std;
     8 const long long N=1e9+7;
     9 typedef long long LL;
    10 LL quickmi(long long  a,long long  b);
    11 LL DP[2*1000005];
    12 void Init()
    13 {
    14     int i,j;
    15     DP[0]=1;
    16     for(i=1;i<=2000005;i++)
    17     {
    18         DP[i]=(DP[i-1]*i)%N;
    19     }
    20 }
    21 int main(void)
    22 {Init();
    23     int i,j,k,p,q;
    24     scanf("%d",&k);
    25     for(i=1;i<=k;i++)
    26     {
    27         scanf("%d %d",&p,&q);
    28         LL ans=quickmi(DP[q-1]*DP[p]%N,N-2);
    29         printf("Case %d: ",i);
    30         printf("%lld
    ",DP[p+q-1]*ans%N);
    31     }
    32     return 0;
    33 }
    34 
    35 LL quickmi(long long  a,long long  b)
    36 {
    37     LL sum=1;
    38     while(b)
    39     {
    40         if(b&1)
    41        sum=(sum*a)%(N);
    42        a=(a*a)%N;
    43        b/=2;
    44     }
    45     return sum;
    46 }
    油!油!you@
  • 相关阅读:
    编译安装httpd
    ANSIBLE安装和常用模块模块使用详细教程
    MySQL集群高可用
    MySQL数据库备份和恢复
    MySQL数据库多表查询
    MySQL语句使用。
    MySQL多实例安装教程
    二进制安装MySQL数据库
    半自动化系统安装
    c语言分别用库函数和系统函数来进行文件操作效率对比
  • 原文地址:https://www.cnblogs.com/zzuli2sjy/p/5223002.html
Copyright © 2020-2023  润新知