题意:给定一个长为n的序列,第i个数a[i]都是一个[1,c]中的整数
如果一段序列[l,r]中出现过的数字出现次数都>=K则称其为好的序列
求最长的好的序列的长度
n,k,c,a[i]<=1e5
思路 :考虑固定右端点,对于每种数字来说合法的左端点都是两段
将对于每种数字来说合法的左端的位置都+1,则和为c的位置都是合法的,显然取最小的左端点
右端点右移的时候推一下左端点如何移动,用一个vector存每种数字出现的位置,往前k个就直接下标减k
1 #include<bits/stdc++.h> 2 using namespace std; 3 typedef long long ll; 4 typedef unsigned int uint; 5 typedef unsigned long long ull; 6 typedef pair<int,int> PII; 7 typedef pair<ll,ll> Pll; 8 typedef vector<int> VI; 9 typedef vector<PII> VII; 10 typedef pair<ll,ll>P; 11 #define N 100010 12 #define M 200010 13 #define fi first 14 #define se second 15 #define MP make_pair 16 #define pi acos(-1) 17 #define mem(a,b) memset(a,b,sizeof(a)) 18 #define rep(i,a,b) for(int i=(int)a;i<=(int)b;i++) 19 #define per(i,a,b) for(int i=(int)a;i>=(int)b;i--) 20 #define lowbit(x) x&(-x) 21 #define Rand (rand()*(1<<16)+rand()) 22 #define id(x) ((x)<=B?(x):m-n/(x)+1) 23 #define ls p<<1 24 #define rs p<<1|1 25 26 const ll MOD=1e9+7,inv2=(MOD+1)/2; 27 double eps=1e-4; 28 int INF=1<<30; 29 ll inf=5e13; 30 int dx[4]={-1,1,0,0}; 31 int dy[4]={0,0,-1,1}; 32 33 int mx[N<<2],tag[N<<2],pos[N<<2],n,C,k; 34 VI c[N]; 35 36 int read() 37 { 38 int v=0,f=1; 39 char c=getchar(); 40 while(c<48||57<c) {if(c=='-') f=-1; c=getchar();} 41 while(48<=c&&c<=57) v=(v<<3)+v+v+c-48,c=getchar(); 42 return v*f; 43 } 44 45 void pushup(int p) 46 { 47 if(mx[ls]>=mx[rs]) 48 { 49 mx[p]=mx[ls]; 50 pos[p]=pos[ls]; 51 } 52 else 53 { 54 mx[p]=mx[rs]; 55 pos[p]=pos[rs]; 56 } 57 } 58 59 void pushdown(int p) 60 { 61 if(tag[p]!=0) 62 { 63 tag[ls]+=tag[p]; 64 tag[rs]+=tag[p]; 65 mx[ls]+=tag[p]; 66 mx[rs]+=tag[p]; 67 tag[p]=0; 68 } 69 } 70 71 void build(int l,int r,int p) 72 { 73 mx[p]=tag[p]=0; 74 pos[p]=l; 75 if(l==r) return; 76 int mid=(l+r)>>1; 77 build(l,mid,ls); 78 build(mid+1,r,rs); 79 } 80 81 void update(int l,int r,int x,int y,int v,int p) 82 { 83 if(l>r) return; 84 if(x>y) return; 85 if(x<=l&&r<=y) 86 { 87 mx[p]+=v; 88 tag[p]+=v; 89 return; 90 } 91 pushdown(p); 92 int mid=(l+r)>>1; 93 if(x<=mid) update(l,mid,x,y,v,ls); 94 if(y>mid) update(mid+1,r,x,y,v,rs); 95 pushup(p); 96 } 97 98 int query(int l,int r,int x,int y,int p) 99 { 100 if(l>r) return 0; 101 if(x>y) return 0; 102 if(mx[p]!=C) return 0; 103 if(x<=l&&r<=y) return pos[p]; 104 pushdown(p); 105 int mid=(l+r)>>1; 106 int res=query(l,mid,x,y,ls); 107 if(res) return res; 108 return query(mid+1,r,x,y,rs); 109 } 110 int main() 111 { 112 while(scanf("%d%d%d",&n,&C,&k)!=EOF) 113 { 114 build(1,n,1); 115 rep(i,1,C) 116 { 117 c[i].clear(); 118 c[i].push_back(0); 119 } 120 int ans=0; 121 rep(i,1,n) 122 { 123 //printf("i=%d ",i); 124 int x=read(); 125 update(1,n,i,i,C-1,1); 126 update(1,n,c[x].back()+1,i-1,-1,1); 127 c[x].push_back(i); 128 int now=(int)c[x].size()-k-1; 129 if(now>=0) update(1,n,c[x][now]+1,c[x][now+1],1,1); 130 int j=query(1,n,1,i,1); 131 if(j) ans=max(ans,i-j+1); 132 } 133 printf("%d ",ans); 134 } 135 136 137 return 0; 138 }