[leetcode]Minimum Window Substring
2017-05-21 20:13
465 查看
Minimum Window Substring
Difficulty:Hard
Given a string S and a string T, find the minimum window in S which will contain all the characters in T in complexity O(n).
For example,
S =
T =
Minimum window is
Note:
If there is no such window in S that covers all characters in T, return the empty string
If there are multiple such windows, you are guaranteed that there will always be only one unique minimum window in S.
题目就是要在S中找到包含T中所有字符的最短子串,包含即可不需要顺序也相同,要求时间复杂度O(n)。
一开始想了几个方法复杂度都不是O(n),想了很久才想出一个办法。
先用一个数组compare记录T中所有字符的重复次数,即ASCii码从33到126的范围内计算,一共93种字符,例如T="aab<"就是2个a、1个b和一个<。
另一个数组match记录当前已满足的字符数,当match中所数都大于等于compare的时候就是找到了一个匹配
例外还有一个链表matchStr记录满足的字符的位置,当match中所有数没有都大于等于compare的时候,其中match大于compare的数就是有多余的字符,应该尽可能的去除这些字符,但是只能从链表的头部开始去除。
当找到了一个匹配后,通过删除去除满足字符的头,让匹配继续往后找。
string minWindow(string s, string t) {
int start = -1;
int end = s.size()+1;//end一开始大于S的size保证第一次匹配时能够赋值
vector<int> compare(93, 0);//需要满足的字符串个数
vector<int> match(93, 0);//已经满足的字符串个数
list<pair<int, char>> matchStr;//满足的字符串
for (int i = 0; i < t.size(); i++){ //计算每个字符需要的数量
compare[(int)(t[i]-33)]++;
}
for (int i = 0; i < s.size(); i++){
if (t.find(s[i]) != t.npos){//判断当前字符是否包含在T中
pair<int, char> p(i, s[i]);//加入满足队列
matchStr.push_back(p);
match[(int)(s[i] - 33)]++;//满足数增加
while (match[(int)(matchStr.front().second - 33)]>compare[(int)(matchStr.front().second - 33)]){//从头开始去除超出的满足字符
match[(int)(matchStr.front().second - 33)]--;
matchStr.pop_front();
}
bool isMatch = true;
for (int j = 0; j < match.size(); j++){//判断当前是否包含足够的字符
if (match[j] < compare[j])
isMatch = false;
}
if (isMatch){//包含足够的字符
if (i - matchStr.front().first < end - start){//是否比已找到的子串更短
start = matchStr.front().first;
end = i;
}
match[(int)(matchStr.front().second - 33)]--;//去除满足字符的头,让匹配继续往后找
matchStr.pop_front();
while (match[(int)(matchStr.front().second - 33)]>compare[(int)(matchStr.front().second - 33)]){//再从头开始去除超出的满足字符
match[(int)(matchStr.front().second - 33)]--;
matchStr.pop_front();
}
}
}
}
if (start < 0 )//通过start判断是否有找到匹配
return "";
else
return s.substr(start, end - start + 1);
}
Difficulty:Hard
Given a string S and a string T, find the minimum window in S which will contain all the characters in T in complexity O(n).
For example,
S =
"ADOBECODEBANC"
T =
"ABC"
Minimum window is
"BANC".
Note:
If there is no such window in S that covers all characters in T, return the empty string
"".
If there are multiple such windows, you are guaranteed that there will always be only one unique minimum window in S.
题目就是要在S中找到包含T中所有字符的最短子串,包含即可不需要顺序也相同,要求时间复杂度O(n)。
一开始想了几个方法复杂度都不是O(n),想了很久才想出一个办法。
先用一个数组compare记录T中所有字符的重复次数,即ASCii码从33到126的范围内计算,一共93种字符,例如T="aab<"就是2个a、1个b和一个<。
另一个数组match记录当前已满足的字符数,当match中所数都大于等于compare的时候就是找到了一个匹配
例外还有一个链表matchStr记录满足的字符的位置,当match中所有数没有都大于等于compare的时候,其中match大于compare的数就是有多余的字符,应该尽可能的去除这些字符,但是只能从链表的头部开始去除。
当找到了一个匹配后,通过删除去除满足字符的头,让匹配继续往后找。
string minWindow(string s, string t) {
int start = -1;
int end = s.size()+1;//end一开始大于S的size保证第一次匹配时能够赋值
vector<int> compare(93, 0);//需要满足的字符串个数
vector<int> match(93, 0);//已经满足的字符串个数
list<pair<int, char>> matchStr;//满足的字符串
for (int i = 0; i < t.size(); i++){ //计算每个字符需要的数量
compare[(int)(t[i]-33)]++;
}
for (int i = 0; i < s.size(); i++){
if (t.find(s[i]) != t.npos){//判断当前字符是否包含在T中
pair<int, char> p(i, s[i]);//加入满足队列
matchStr.push_back(p);
match[(int)(s[i] - 33)]++;//满足数增加
while (match[(int)(matchStr.front().second - 33)]>compare[(int)(matchStr.front().second - 33)]){//从头开始去除超出的满足字符
match[(int)(matchStr.front().second - 33)]--;
matchStr.pop_front();
}
bool isMatch = true;
for (int j = 0; j < match.size(); j++){//判断当前是否包含足够的字符
if (match[j] < compare[j])
isMatch = false;
}
if (isMatch){//包含足够的字符
if (i - matchStr.front().first < end - start){//是否比已找到的子串更短
start = matchStr.front().first;
end = i;
}
match[(int)(matchStr.front().second - 33)]--;//去除满足字符的头,让匹配继续往后找
matchStr.pop_front();
while (match[(int)(matchStr.front().second - 33)]>compare[(int)(matchStr.front().second - 33)]){//再从头开始去除超出的满足字符
match[(int)(matchStr.front().second - 33)]--;
matchStr.pop_front();
}
}
}
}
if (start < 0 )//通过start判断是否有找到匹配
return "";
else
return s.substr(start, end - start + 1);
}
相关文章推荐
- LeetCode76 Minimum Window Substring(两种解法)
- LeetCode_Minimum Window Substring
- Leetcode-76 Minimum Window Substring
- Leetcode Minimum Window Substring
- [LeetCode] Minimum Window Substring
- [leetcode-76]Minimum Window Substring(java)
- LeetCode —— Minimum Window Substring
- leetcode — minimum-window-substring
- Leetcode: Minimum Window Substring
- [leetcode] Minimum Window Substring
- Minimum Window Substring - LeetCode
- LEETCODE: Minimum Window Substring
- 【LeetCode】 Minimum Window Substring
- LeetCode Minimum Window Substring
- [LeetCode] Minimum Window Substring
- LeetCode76 Minimum Window Substring(两种解法)
- [Leetcode] Minimum Window Substring
- LeetCode -- Minimum Window Substring
- LeetCode 76 Minimum Window Substring
- LeetCode Minimum Window Substring