Week5 C - 平衡字符串
一个长度为 n 的字符串 s,其中仅包含 ‘Q’, ‘W’, ‘E’, ‘R’ 四种字符。
如果四种字符在字符串中出现次数均为 n/4,则其为一个平衡字符串。
现可以将 s 中连续的一段子串替换成相同长度的只包含那四个字符的任意字符串,使其变为一个平衡字符串,问替换子串的最小长度?
如果 s 已经平衡则输出0。
Input
一行字符表示给定的字符串s
Output
一个整数表示答案
Examples
Input
QWER
Output
0
Input
QQWE
Output
1
Input
QQQW
Output
2
Input
QQQQ
Output
3
Note
1<=n<=10^5
n是4的倍数
字符串中仅包含字符 ‘Q’, ‘W’, ‘E’ 和 ‘R’.
解题思路
利用滑动窗口 [ L , R ]
当条件符合时 L++ 当条件不符合时 R++
窗口内判断 MAX=mm(sum1,sum2,sum3,sum4)
TOTAL = R - L + 1 当前窗口长度
free=TOTAL-((MAX-sum1)+(MAX-sum2)+(MAX-sum3)+(MAX-sum4));
当 free >= 0 且 free 的值是 4 的倍数时 符合条件
Code
#include<iostream>
#include <algorithm>
#include <cstring>
using namespace std;
string s;
int sum1=0,sum2=0,sum3=0,sum4=0;
int mm(int s1,int s2,int s3,int s4){
return max(max(s1,s2),max(s3,s4));
}
int main(){
cin>>s;
int sl=s.length();
//cout<<s[0]<<' '<<s[1]<<' '<<s[2]<<' '<<s[3]<<endl;
for(int i=0;i<sl;i++){
switch(s[i]){
case'Q':
sum1++;break;
case'W':
sum2++;break;
case'E':
sum3++;break;
case'R':
sum4++;break;
}
}
//cout<<sum1<<' '<<sum2<<' '<<sum3<<' '<<sum4<<endl;
if(sum1==sum2&&sum2==sum3&&sum3==sum4){
cout<<0;
return 0;
}
switch(s[0]){
case'Q':
sum1--;break;
case'W':
sum2--;break;
case'E':
sum3--;break;
case'R':
sum4--;break;
}
int r=0,l=0;
int ans=10000000;
while(1){
//for(int i=l;i<=r;i++)cout<<s[i]<<' ';
int MAX=mm(sum1,sum2,sum3,sum4);
int total=r-l+1;
int free=total-((MAX-sum1)+(MAX-sum2)+(MAX-sum3)+(MAX-sum4));//cout<<total<<endl;
if(free>=0&&free%4==0){//cout<<"go l"<<endl;
if(ans>total)ans=total;
switch(s[l]){
case'Q':
sum1++;break;
case'W':
sum2++;break;
case'E':
sum3++;break;
case'R':
sum4++;break;
}
l++;
}else{//cout<<"go r"<<endl;
if(r+1<sl)r++;
else break;
switch(s[r]){
case'Q':
sum1--;break;
case'W':
sum2--;break;
case'E':
sum3--;break;
case'R':
sum4--;break;
}
}
}
cout<<ans;
}