[Leetcode] 727. Minimum Window Subsequence 解题报告

题目

Given strings S and T, find the minimum (contiguous) substring W of S, so that T is a subsequence of W.

If there is no such window in S that covers all characters in T, return the empty string "". If there are multiple such minimum-length windows, return the one with the left-most starting index.

Example 1:

Input: 
S = "abcdebdde", T = "bde"
Output: "bcde"
Explanation: 
"bcde" is the answer because it occurs before "bdde" which has the same length.
"deb" is not a smaller window because the elements of T in the window must occur in order.

Note:

All the strings in the input will only contain lowercase letters. The length of  S will be in the range  [1, 20000]. The length of  T will be in the range  [1, 100].

思路

动态规划问题。我们定义dp[i][j]表示S的前缀S[0,i]中的起始索引k,使得T[0,j]是S[k,i]的子串。这样如果S[i] == T[0],则dp[i][0] = i,否则dp[i][0] = -1。而递推公式为:如果S[i] == T[j],那么dp[i][j] = max(dp[k][j-1]), 0 <= k < i。否则dp[i][j] = -1。而我们的目标则是找到min(i - dp[i][n-1]),其中n是T的长度。

代码

class Solution {
public:
    string minWindow(string S, string T) {
        int m = S.size(), n = T.size();
        vector> dp(n, vector(m, -1));
        for (int i = 0; i < m; ++i) {       // initialization
            if (S[i] == T[0]) {
                dp[0][i] = i;
            }
        } 
        for (int j = 1; j < n; ++j) {       // find the correct starting index
            int k = -1;
            for (int i = 0; i < m; i++) {
                if (k != -1 && S[i] == T[j]) {
                    dp[j][i] = k;
                }
                if (dp[j-1][i] != -1) {
                    k = dp[j-1][i];
                }
            }
        }
        int st = -1, len = INT_MAX;         // find the minimal length
        for (int i = 0; i < m; ++i) {
            if (dp[n-1][i] != -1 && i - dp[n-1][i] + 1 < len) {
                st = dp[n-1][i];
                len = i - dp[n-1][i] + 1;
            }    
        }
        return st == -1? "" : S.substr(st, len);
    }
};

你可能感兴趣的:(IT公司面试习题)