洛谷:
P2697 宝石串 - 洛谷 | 计算机科学教育新生态 (luogu.com.cn)
宝石串
题目描述:
有一种宝石串,由绿宝石和红宝石串成,仅当绿宝石和红宝石数目相同的时候,宝石串才最为稳定,不易断裂。安安想知道从给定的宝石串中,可以截取一段最长的稳定的宝石串,有多少颗宝石组成。请你帮助他。
绿宝石用 G 表示,红宝石用 R 表示。
输入格式
一行,一个由 G 和 R 组成的字符串。
输出格式
一行一个整数,表示最长的稳定的宝石串有多少颗宝石组成。
输入数据 1
Copy
GRGGRG
输出数据 1
Copy
4
提示
RGGR为答案。
宝石数小于等于 1000000。
解题思路:
把G作为-1,R作为1,存放于a结构体数组数组(包含序号与数字);对A做前缀和;再排序(数字一样序号小在前,数字不一样数字小在前),用双指针遍历排序后的A找出最长相同子序列,首尾序号相减得个数,但num为0得特判。
例:GRGGRG->G GRGGR -> GRGGR - G = RGGR
A[i]=-1 A[j]=-1 A[i] - A[j]
-1 - -1 = 0
代码:
#include<bits/stdc++.h>
using namespace std;
struct node{
int num,id;
};
bool cmp(node p1,node p2){
if(p1.num==p2.num){
return p1.id<p2.id;
}
return p1.num<p2.num;
}
node b[1000010];
int main(){
string s;
cin>>s;
for(int i=0;i<s.size();i++){
int x;
if(s[i]=='G'){
x=-1;
}else{
x=1;
}
b[i+1].num=b[i].num+x;
b[i+1].id=i+1;
}
sort(b+1,b+s.size()+1,cmp);
int t=0,st=0;
for(int i=1,j=1;j<=s.size();j++){
if(b[j].num==b[i].num){
t=b[j].id-b[i].id;
}else if(t>=st){
st=t;
i=j;
t=0;
}else{
i=j;//这一块要注意,无论是否更新st,都要重置,我不知道大家有没有这种问题。反正笔者踩过坑
t=0;
}
if(b[j].num==0&&b[j].id>st){
st=b[j].id;
}
}
cout<<st<<endl;
return 0;
}