【leetcode刷题笔记】Minimum Window Substring

时间:2014-07-26 14:50:20   收藏:0   阅读:326

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 emtpy string "".

If there are multiple such windows, you are guaranteed that there will always be only one unique minimum window in S.


 

题解:参考leetcode给出的解答,实现了O(n)的算法。

用到的主要变量如下:

设置一个Map:ToFind记录T中出现的字符的种类和个数,我们需要在S中找到这些字符。

设置另一个Map:hasFound记录当前窗口中包含的字符的种类和个数。

这两个Map,结合一个变量count——在当前窗口中找到的T中的字符个数,我们就可以判断当前窗口是否包含T中所有的字符了。

算法的主要过程如下:

举个例子:S = "acbbaca" , T = "aba"。

bubuko.com,布布扣

如上图所示,end从初始的位置扩展到下面的图中的位置时候,窗口包含了T中所有的字符,而且begin也无法挪动了,此时得到一个最小窗口长度为5;

bubuko.com,布布扣

接下来继续移动end直到下一个包含在T里面的元素处(见第二幅图),然后把begin尽可能往右移动(见第三幅图),得到一个新的当前最小窗口baca,由于它比最小窗口acbba短,所以更新最小窗口为baca。算法结束。

所以我们可以看出begin只有在找到T的时候才右移收缩窗口,而end一直后移。在找到第一个窗口后,end每移动到一个T里面包含的元素处,就会有一个新的窗口(比如上述end从索引为4的地方挪动到索引为6的地方)。

代码如下:

 1 public class Solution {
 2     public String minWindow(String S, String T) {
 3         HashMap<Character, Integer> needToFind = new HashMap<Character, Integer>();
 4         HashMap<Character, Integer> hasFound = new HashMap<Character, Integer>();
 5         int count = 0;
 6         
 7         for(int i = 0;i < T.length();i++){
 8             char ch_t = T.charAt(i);
 9             if(!needToFind.containsKey(ch_t)){
10                 needToFind.put(ch_t, 1);
11                 hasFound.put(ch_t, 0);
12             }
13             else {
14                 needToFind.put(ch_t, needToFind.get(ch_t)+1);
15             }
16         }
17         
18         int minWindowBegin = -1;
19         int minWindowEnd = S.length();
20         int minWindowLen = S.length();
21         for(int begin = 0,end = 0; end < S.length();end++){
22             char char_end = S.charAt(end);
23             //skip character not in T
24             if(!needToFind.containsKey(char_end))
25                 continue;
26             hasFound.put(char_end, hasFound.get(char_end)+1);
27             if(hasFound.get(char_end) <= needToFind.get(char_end))
28                 count++;
29             
30             if(count == T.length()){
31                 //narrow down the window as much as possible
32                 char char_begin = S.charAt(begin);
33                 while(!needToFind.containsKey(char_begin) || hasFound.get(char_begin) > needToFind.get(char_begin)){
34                     if(needToFind.containsKey(char_begin) && hasFound.get(char_begin) > needToFind.get(char_begin)){
35                         hasFound.put(char_begin, hasFound.get(char_begin)-1);
36                     }
37                     begin++;
38                     char_begin = S.charAt(begin);
39                 }
40                 
41                 int windowLen = end - begin + 1;
42                 if(windowLen <= minWindowLen){
43                     minWindowBegin = begin;
44                     minWindowEnd = end;
45                     minWindowLen = windowLen;
46                 }
47                     
48             }
49         }
50         
51         if(count == T.length()){
52             StringBuffer sbBuffer = new StringBuffer();
53             for(int i = minWindowBegin;i<=minWindowEnd;i++)
54                 sbBuffer.append(S.charAt(i));
55             return sbBuffer.toString();
56         }
57         else
58             return "";        
59     }
60 }

 

【leetcode刷题笔记】Minimum Window Substring,布布扣,bubuko.com

评论(0
© 2014 mamicode.com 版权所有 京ICP备13008772号-2  联系我们:gaon5@hotmail.com
迷上了代码!