题目链接
题目大意:对一个有
n(1<=n<=106)
个数的数列使用冒泡排序,需要排
k
轮。求
毫无疑问暴力会无限TLE……
找找规律就发现冒泡排序的轮数与逆序对有关,
例如数列:
1,3,4,2
其中
2
的逆序对最多为
现在的事情就是构造一个最大逆序对为
k
的排列。现将
令
那么
所求的答案为
g(k)−g(k−1)
#include <iostream>
#include <cstdio>
#define ymx 20100713
#define LL long long int
using namespace std;
int n ,k ;
LL fact[1000005] ,ans ;
LL power(LL a,LL pos)
{
LL ans=1;
while(pos>0)
{
if(pos&1)
ans=ans*a%ymx;
a=a*a%ymx;
pos>>=1;
}
return ans;
}
LL g(int k)
{
return fact[k]*power(k+1,n-k)%ymx ;
}
int main()
{
int T ;
scanf("%d",&T) ;
fact[0]=fact[1]=1 ;
for(int i=2;i<=1000000;++i)
fact[i]=fact[i-1]*i%ymx;
while(T--)
{
scanf("%d%d",&n,&k);
if(k==0)puts("1");
else
{
ans=g(k)-g(k-1) ;
if(ans<0)ans+=ymx;
printf("%I64d\n",ans);
}
}
return 0;
}