Leetcode 316. 去除重复字母(中等) 1081. 不同字符的最小子序列(中等) 字符串去重
题目:
思路:
题目的要求总结出来有三点:
要求一、要去重。
要求二、去重字符串中的字符顺序不能打乱 s
中字符出现的相对顺序。
要求三、在所有符合上一条要求的去重字符串中,字典序最小的作为最终结果。
比如说输入字符串 s = "babc"
,去重且符合相对位置的字符串有两个,分别是 "bac"
和 "abc"
,但是我们的算法得返回 "abc"
,因为它的字典序更小。
我们可以借用单调栈的思路,在放入元素c时踢出大于c的元素。
但是踢出的条件是,如果count[d]>0,即后续仍旧有d可以加入。
class Solution { public: string removeDuplicateLetters(string s) { // 维护一个计数器记录字符串中字符的数量 // 因为输入为 ASCII 字符,大小 256 够用了 vector<int> count(256); for(int i=0;i<s.size();++i){ count[s[i]]++; } //记录字符是否已进栈 vector<bool> inStack(256); stack<char> stk; for(int i=0;i<s.size();++i){ char c=s[i]; // 每遍历过一个字符,都将对应的计数减一 count[c]--; //如果已进栈,就直接跳过 if(inStack[c]){ continue; } //如果栈顶元素大于c,对栈顶元素操作 while(!stk.empty()&&stk.top()>c){ // 若之后不存在栈顶元素了,则停止 pop if(count[stk.top()]==0){ break; } // 若之后还有,则可以 pop inStack[stk.top()]=false; stk.pop(); } stk.push(c); inStack[c]=true; } //反序取出栈内元素组合成字符串 string ret; while(!stk.empty()){ ret=stk.top()+ret; stk.pop(); } return ret; } };
与上题完全相同
联系方式:emhhbmdfbGlhbmcxOTkxQDEyNi5jb20=