Leetcode——97. Interleaving String

问题描述:

Given s1s2s3, find whether s3 is formed by the interleaving of s1 and s2.

For example,
Given:
s1 = "aabcc",
s2 = "dbbca",

When s3 = "aadbbcbcac", return true.
When s3 = "aadbbbaccc", return false.

解题思路:

首先可以这么考虑,s3一定是s1和s2组成,用s3[i]表示s3的前 i 位,它一定由s1的前m位s1[m]和s2的前n位s2[n]组成,其中m+n=i. 这种情况下我们遍历所有组成情况就好了。

比如 i = 4,只需要判断 (s1[0],s2[4]),(s1[1],s2[3]),(s1[2],s2[2]),(s1[3],s2[1]), (s1[4],s2[0]). 

这样看的话DFS就可以搞了,但是为了更高效,我还是找找DP是不是可以搞。

递推公式这样,建立二维数组, 假设p[m][n]表示(s1[m],s2[n])可不可以表达(m+n+长度的s3。这时只需要考虑p[i-1][j] 和p[i][j-1]两个位置:

   1.  第一种情况是:p[m-1][n] == true && s1[m] = s3[i],这意味着(s1[m-1],s2[n])可以组成 s3[m+n-1]长度的串,如果s1的第m位 s1[m] == s3的第m+n位,s3[i],那么p[m][n] 就是可匹配的。

   2.第二种情况是: p[m][n-1] == true && s2[n] = s3[i],同上分析,只不过s3的第m+n位是s2[n]匹配的而已。


我做了下简化,用好了一维数组,看过背包九讲的大概知道DP可以把空间复杂度从二维降到一维。只是遍历的时候是逆序,并且注意下边界判断即可:

class Solution {
public:
    bool isInterleave(string s1, string s2, string s3) {
        int m = s1.size();
        if(m + s2.size() != s3.size()) return false;
        bool t[m + 1];
        t[0] = 1;
        for(int i = 0; i < s3.size(); i++){
            bool ct = true;
            for(int j = min(m,i + 1); j > 0; j--){
                if(t[j] && s2[i - j] == s3[i]) ct = false;
                else if(t[j - 1] && s1[j - 1] == s3[i]) { t[j] = true; ct = false;} 
                else t[j] = false;
            }
            if(t[0] && s2[i] == s3[i]) ct = false;
            if(ct) return false;
        }
    	return true;
    }
}; 



评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值