HDOJ 5646 DZY Loves Partition

来源:互联网 发布:淘宝企业店铺是真货么 编辑:程序博客网 时间:2024/04/28 11:02

DZY Loves Partition

Time Limit: 4000/2000 MS (Java/Others)    Memory Limit: 262144/262144 K (Java/Others)
Total Submission(s): 117    Accepted Submission(s): 38


Problem Description
DZY loves partitioning numbers. He wants to know whether it is possible to partitionn into the sum of exactly k distinct positive integers.

After some thinking he finds this problem is Too Simple. So he decides to maximize the product of thesek numbers. Can you help him?

The answer may be large. Please output it modulo 109+7.
 

Input
First line contains t denoting the number of testcases.

t testcases follow. Each testcase contains two positive integers n,k in a line.

(1t50,2n,k109)
 

Output
For each testcase, if such partition does not exist, please output1. Otherwise output the maximum product mudulo 109+7.
 

Sample Input
43 43 29 3666666 2
 

Sample Output
-1224110888111
Hint
In 1st testcase, there is no valid partition.In 2nd testcase, the partition is $3=1+2$. Answer is $1\times 2 = 2$.In 3rd testcase, the partition is $9=2+3+4$. Answer is $2\times 3 \times 4 = 24$. Note that $9=3+3+3$ is not a valid partition, because it has repetition.In 4th testcase, the partition is $666666=333332+333334$. Answer is $333332\times 333334= 111110888888$. Remember to output it mudulo $10^9 + 7$, which is $110888111$.


#include <iostream>#include<cstdio>#include<cstring>#include<cmath>#define MOD 1000000007using namespace std;int main(){    int t,i;    __int64 s,n,k;    scanf("%d",&t);    while(t--)    {        s=1;        scanf("%I64d%I64d",&n,&k);        if(n<k*(k+1)/2)        {            printf("-1\n");            continue;        }        if(n%k==0)        {            int tem=n/k;            if(k&1)                s=tem;//这里竟然写成k。。。。我真是个。。。。            for(i=1;i<=k/2;++i)                s=s*(tem-i)*(tem+i)%MOD;        }        else        {            int tem=k*(k-1)/2;//这里将第一个数看做基数,这里加和的是之后的k-1个数在基数上的增量(这里先将这k个数看为连续的)            int num=(n-tem)%k;//将这些增量都减去再取余就得到若是这k个数如此取加和之后与n的差量(需将这些差量补充到k个数中)            int base=(n-tem)/k;//求基数。因为要求乘积最大所以这些增量需要一个一个的加到后num个数上)            i=1;            for(;i<=num;++i)            {                s=s*(base+k-i+1)%MOD;//这里就是要加1的乘积            }            while(i<=k)                s=s*(base+k-i++)%MOD;//不加1的乘积        }        printf("%I64d\n",s);    }    return 0;}


0 0