【LeetCode】76. Minimum Window Substring

Minimum Window Substring

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.

 

由于大小写字母的ASCII码不大于128,因此开辟两个数组存储信息。

needFind数组存储T字符串每个字符出现次数。例如:needFind['A']=5意为T中A出现5次。

Found数组存储S字符串在[begin,end]窗口内每个字符出现次数。

算法核心思想如下:

在保证[begin,end]窗口包含T中所有字符的条件下,延伸end,收缩begin。

进行一次扫描后,记录符合条件的最小窗口(end-begin+1)表示的字符串。

有个问题:怎样才知道[begin,end]窗口包含了T中所有字符?

我使用count记录剩余“有效”字符数,当count达到0时,即可说明[begin,end]包含了T。

注意:“有效”的意思是指,当前延伸得到的S[end]字符,使得[begin,end]更进一步包含T,而不是重复劳动。

比如说,T="a", [begin,end]已经包含"a",再延伸得到"aa",只是无效操作,并没有使得[begin,end]更接近T,有效字符数仍为1.

 

class Solution {
public:
    string minWindow(string S, string T) {
        int begin = 0;
        int end = 0;
        int minbegin = 0;
        int minend = 0;
        int minSize = INT_MAX;
        vector<int> needFind(128, 0);
        vector<int> Found(128, 0);
        for(int i = 0; i < T.size(); i ++)
            needFind[T[i]] ++;
        Found[S[0]] ++;
        int count = T.size();
        if(needFind[S[0]] >= Found[S[0]])
            count --;
        while(true)
        {
            if(count == 0)
            {//shrink begin
                while(Found[S[begin]] > needFind[S[begin]])
                {
                    Found[S[begin]] --;
                    begin ++;
                }
                int size = end-begin+1;
                if(size < minSize)
                {
                    minbegin = begin;
                    minend = end;
                    minSize = size;
                }
            }
            if(end < S.size())
            {
                end ++;
                Found[S[end]] ++;
                if(needFind[S[end]] >= Found[S[end]])
                    count --;
            }
            else
                break;
        }
        if(minSize != INT_MAX)
            return S.substr(minbegin, minSize);
        else
            return "";
    }
};

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值