Codeforces Round #596 (Div. 2)B2. TV Subscriptions(Hard Version)
题目:http://codeforces.com/contest/1247/problem/B2
题意:给出一个序列,可以选择K个数字,标记选择的数字,求能够在原序列中有连续d个数字被标记的最小的K
做法:记录下长度为d的区间中,存在多少个不同的数字。发现区间长度是一定的,就可以不断递推过去
AC代码:
#include <bits/stdc++.h>
#define ll long long
#define pb push_back
#include<set>
#define rep(x,a,b) for(int x=a;x<=b;x++)
using namespace std;
const int maxn=2e6+7;
int a[maxn];
int num[maxn];
int main()
{
int t,n,k,d;
scanf("%d",&t);
while(t--)
{
int ans=0,maxx=0;
scanf("%d%d%d",&n,&k,&d);
rep(i,1,n){scanf("%d",&a[i]);num[a[i]]=0;}
for (int i=1;i<=d;i++)
{
if (num[a[i]]==0)ans++;
num[a[i]]++;
}
int minn=ans;
for (int i=d+1;i<=n;i++)
{
if (a[i]==a[i-d])continue;
else
{
//区间右端点
if (num[a[i]]==0) ans++;
num[a[i]]++;
//区间左端点
if (num[a[i-d]]==1) ans--;
num[a[i-d]]--;
}
minn=min(minn,ans);
}
cout<<minn<<endl;
}
}