leetcode周赛285T4-由单个字符重复的最长子字符串

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

我的方案(利用有序集合维护 超时)

  • 对于每一段相同字母都利用有序集合记录(即红黑树)。开始和长度
  • 并利用map记录现有长度和长度个数
  • 每次插入,查找,删除都是 O ( n l o g n ) O(nlogn) O(nlogn)?
  • 感觉复杂度也是 O ( l o g n ) O(logn) O(logn)
  • 应该是被卡常了?
#include<iostream>
#include<vector>
#include<string>
#include<set>
#include<algorithm>
#include<map>
using namespace std;

struct node
{
    int st;  //startindex
    int length;  //长度

    bool operator<(const node &other) const
	{
		return st < other.st;
	}

};

void PRINT(set<node> a[26],char ch)
{
    cout << "below:a,ch = "<<ch << endl;
    set<node>::iterator iter;
    for(iter=a[ch-'a'].begin();iter!=a[ch-'a'].end();iter++)
    {cout << iter->st<<endl; cout << iter->length<<endl;}
}

class Solution {
public:
    vector<int> longestRepeating(string s, string queryCharacters, vector<int>& queryIndices) {
        vector<int> ans;
        set<node> a[26];
        map<int,int,greater<int>> b;  //记录长度与个数
        int i = 0;
        for(int j = 0;j<26;j++) {struct node temp;temp.st=999999;a[j].insert(temp);}
        while(i<s.size())
        {
            char cur=s[i];int j = i;
            while(i<s.size()&&s[i]==cur) i++;
            struct node l; l.length=i-j;l.st=j;
            if(b.find(i-j)!=b.end()) b[i-j]++; else b[i-j]=1;
            a[cur-'a'].insert(l);
        }
       // for(map<int,int>::iterator it=b.begin();it!=b.end();it++) cout<<it->first<<endl;
        for(i = 0;i<queryCharacters.size();i++)
        {
            int ind = queryIndices[i]; 
            char ch = queryCharacters[i];
            //PRINT(a,ch);
            char now = s[ind]; struct node temp; temp.length=0;temp.st=ind;
            set<node>::iterator iter = upper_bound(a[now-'a'].begin(),a[now-'a'].end(),temp);
            iter--;   //最后一个小于等于的
            int st = iter->st; int end = st + iter->length - 1;
            b[iter->length]--; 
            if(b[iter->length] == 0) b.erase(iter->length);
            a[now-'a'].erase(iter); //删除
            if(ind-st>0) {
                struct node temp;temp.st=st;temp.length=ind-st;
                a[now-'a'].insert(temp);
                if(b.find(temp.length)!=b.end()) b[temp.length]++;
                else b[temp.length]=1;
            }
            if(end-ind>0)
            {
                struct node temp; temp.st=ind+1;temp.length=end-ind;
                a[now-'a'].insert(temp);
                if(b.find(temp.length)!=b.end()) b[temp.length]++;
                else b[temp.length]=1;
            }
            //插入
            bool left=true;bool right = true;
            if(ind-1<0||s[ind-1]!=ch)left=false;
            if(ind+1>=s.size()||s[ind+1]!=ch)right=false;
            s[ind]=ch;
            if(left&&right)  //左右均和当前字符相同
            {
                int length = 0;
                struct node tmp;tmp.st=ind;  
                set<node>::iterator iter1= upper_bound(a[ch-'a'].begin(),a[ch-'a'].end(),tmp);
                length+=iter1->length;
                set<node>::iterator iter2 = iter1;
                iter2--; 
                b[iter1->length]--; if(b[iter1->length]==0) b.erase(iter1->length);
                b[iter2->length]--; if(b[iter2->length]==0) b.erase(iter2->length);
                int begin=iter2->st; length+=iter2->length;
                a[ch-'a'].erase(iter1); a[ch-'a'].erase(iter2);
                struct node temp; temp.st=begin;temp.length=length+1;
                a[ch-'a'].insert(temp);
                if(b.find(temp.length)!=b.end()) b[temp.length]++; else b[temp.length]=1;
            }
            else if(!left&&right)  //和右侧相同
            {
                struct node tmp;tmp.st=ind;
                set<node>::iterator iter1 = upper_bound(a[ch-'a'].begin(),a[ch-'a'].end(),tmp);
                int length=iter1->length;
                a[ch-'a'].erase(iter1);
                b[iter1->length]--; if(b[iter1->length]==0) b.erase(iter1->length);
                struct node temp; temp.st=ind;temp.length=1+length; 
                a[ch-'a'].insert(temp);
                if(b.find(temp.length)!=b.end()) b[temp.length]++; else b[temp.length]=1;
            }
            else if(left&&!right)  //和左侧相同
            {
                struct node tmp;tmp.st=ind;
                set<node>::iterator iter1=lower_bound(a[ch-'a'].begin(),a[ch-'a'].end(),tmp);
                iter1--;     //最后一个小于等于的
                b[iter1->length]--; if(b[iter1->length]==0) b.erase(iter1->length);
                struct node temp; temp.length=iter1->length+1;temp.st=iter1->st;
                a[ch-'a'].erase(iter1);
                a[ch-'a'].insert(temp);  //插入temp
                if(b.find(temp.length)!=b.end()) b[temp.length]++; else b[temp.length]=1;
            }
            else{                       //左右两侧都不同,直接插入
                struct node temp; temp.length=1;temp.st=ind;
                a[ch-'a'].insert(temp);
                if(b.find(temp.length)!=b.end()) b[temp.length]++; else b[temp.length]=1;
            }
            //cout << "this is b" << endl;
            //cout << b.begin()->first << endl;
            ans.push_back(b.begin()->first);
        }
        //system("pause");
        return ans;    
    }
};

int main()
{
    vector<int> a;
    a.push_back(1);a.push_back(3);a.push_back(3);
    vector<int> ans = (new Solution)->longestRepeating("babacc","bcb",a);
    for(int i  =0;i<ans.size();i++) cout << ans[i] << endl;
    system("pause");
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值