DZY Loves Partition
Time Limit: 4000/2000 MS (Java/Others) Memory Limit: 262144/262144 K (Java/Others)Total Submission(s): 1444 Accepted Submission(s): 552
Problem Description
DZY loves partitioning numbers. He wants to know whether it is possible to partition
n
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 these k numbers. Can you help him?
The answer may be large. Please output it modulo 109+7 .
After some thinking he finds this problem is Too Simple. So he decides to maximize the product of these k 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.
( 1≤t≤50,2≤n,k≤109 )
t testcases follow. Each testcase contains two positive integers n,k in a line.
( 1≤t≤50,2≤n,k≤109 )
Output
For each testcase, if such partition does not exist, please output
−1
. Otherwise output the maximum product mudulo
109+7
.
Sample Input
4 3 4 3 2 9 3 666666 2
Sample Output
-1 2 24 110888111HintIn 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$.
Source
#include<bits/stdc++.h>
using namespace std;
const int mod = 1e9+7;
int main(void)
{
long long t, n, k, ans;
cin >> t;
while(t--)
{
ans = 1;
scanf("%lld%lld", &n, &k);
if((1+k)*k/2 > n) puts("-1");
else
{
if(n%k == 0)
{
long long avg = (n/k);
if(k%2) ans = avg;
for(int i = 1; i <= k/2; i++)
ans = ans*(avg-i)*(avg+i)%mod;
}
else
{
//base, base+1, base+2....base+k-1
//sum是假设连续,相对第一个数,后面的k-1个数多加的值
long long sum = (k-1)*k/2;
//若不连续,num不为0,num的值为需多加的1
long long num = (n-sum)%k;
long long base = (n-sum)/k;
long long i;
//因为要乘积最大,所以要从后面开始数的num个数加1
for(i = 1; i <= num; i++)
ans = ans*(base+k+1-i)%mod;
while(i <= k)
ans = ans*(base+k-i++)%mod;
}
printf("%lld\n", ans);
}
}
return 0;
}