版权声明:原创,未经作者允许禁止转载 https://blog.csdn.net/Mr_wuyongcong/article/details/89276136
正题
题目大意
求有多少个长度为 且由 组成的序列满足在求最大值时交换了 次。
解题思路
考虑 预处理。
用 表示长度为 ,最大的数是 ,交换了 次
显然有
对于
我们可以前缀和优化到
然后我们要考虑最大的不一定是 ,所以
时间复杂度
#include<cstdio>
#include<cstring>
#include<algorithm>
#define ll long long
using namespace std;
const ll XJQ=1e9+7;
ll t,f[110][310][110],n,k,p,ans,sum[310][110];
int main()
{
scanf("%lld",&t);
for(ll i=1;i<=300;i++)
f[1][i][1]=1;
for(ll j=1;j<=300;j++)
sum[j][1]=(sum[j-1][1]+f[1][j][1])%XJQ;
for(ll i=2;i<=100;i++)
{
for(ll j=1;j<=300;j++)
for(ll k=1;k<=min(i,j);k++)
f[i][j][k]=(f[i-1][j][k]*j%XJQ+sum[j-1][k-1])%XJQ;
memset(sum,0,sizeof(sum));
for(ll j=1;j<=300;j++)
for(ll k=1;k<=i;k++)
sum[j][k]=(sum[j-1][k]+f[i][j][k]%XJQ);
}
while(t--){
scanf("%lld%lld%lld",&n,&k,&p);
p++;ans=0;
for(ll i=1;i<=k;i++)
ans=(ans+f[n][i][p])%XJQ;
printf("%lld\n",ans);
}
}