思路: 如果不要求复杂度为n的话这题还挺简单的,brute force解法就行。找出s所有substring,再判断下是否含有t中的全部字符。最后在所有合法的substring中挑一个长度最短的就好了。不过这样复杂度应该是n^3了。所以这题要用到一个重要的算法sliding window。这个算法在求substring中类的问题上还是很有效的,很多题可以套用这个算法。下面搬运一下lc上介绍的sliding window算法:
再搬运一下discussion区域别人针对该题解释的sliding window算法:
这个算法可以说是一个模版,在求substring的问题,一般都可以套用该算法。那么下面我直接搬运一下lc上别人的high votes答案。确实挺难的,我看别人的答案也看了好久才看明白在干嘛。这种题目我估摸着面试我是做不出来的,但是多去思考思考也是好事,锻炼自己的大脑。代码如下:
string minWindow(string s, string t) {
unordered_map<char, int> m;
// Statistic for count of char in t
for (auto c : t) m[c]++;
// counter represents the number of chars of t to be found in s.
size_t start = 0, end = 0, counter = t.size(), minStart = 0, minLen = INT_MAX;
size_t size = s.size();
// Move end to find a valid window.
while (end < size) {
// If char in s exists in t, decrease counter
if (m[s[end]] > 0)
counter--;
// Decrease m[s[end]]. If char does not exist in t, m[s[end]] will be negative.
m[s[end]]--;
end++;
// When we found a valid window, move start to find smaller window.
while (counter == 0) {
if (end - start < minLen) {
minStart = start;
minLen = end - start;
}
m[s[start]]++;
// When char exists in t, increase counter.
if (m[s[start]] > 0)
counter++;
start++;
}
}
if (minLen != INT_MAX)
return s.substr(minStart, minLen);
return "";
}
总结:
- 多尝试用sliding window算法去解答substring类型的问题。可以有效减低复杂度。