题意:给定序列,给定正整数k m,问有多少个子序列满足
分析:升序排序,枚举每个位置相当于是子序列中最小的那个元素,然后二分查找第一个大于a[i]+k的位置index, 接下来就相当于在区间 [i+1,index-1] 中任意找出m-1个元素就好 ,也就是求个组合数,可以先打好表。
#include<bits/stdc++.h>
using namespace std;
#define ll long long
#define pii pair<int,int>
const int maxn = 2e5+5;
const int mx = 40;
const int mod = 1e9+5;
const ll inf = 34359738370;
const int INF = 1e9+7;
int n,a[maxn];
int m,k;
ll c[maxn][105];//杨辉三角
int main()
{
for(int i=0;i<=maxn;i++)
{
c[i][0]=1;
for(int k=1;k<=min(i,101);k++)
{
c[i][k]=(c[i-1][k-1]+c[i-1][k])%INF;
}
}
int t;
scanf("%d",&t);
while(t--)
{
scanf("%d %d %d",&n,&m,&k);
for(int i=1;i<=n;i++) scanf("%d",a+i);
sort(a+1,a+n+1);
ll ans=0;
for(int i=1;i<=n;i++)
{
int index=upper_bound(a+1,a+n+1,a[i]+k)-a;
int r=index-i;//[i+1,index-1]中 选m-1个
if(r<m) continue;
ans=(ans+c[r-1][m-1])%INF;
}
printf("%I64d\n",ans);
}
return 0;
}