题目:Givens1 , s2 , s3 , find whethers3 is formed by the interleaving ofs1 ands2 .
For example,
Given:
s1 ="aabcc" ,
s2 ="dbbca" ,
Whens3 = "aadbbcbcac" , return true.
Whens3 = "aadbbbaccc" , return false.
“When you see string problem that is about subsequenceor matching, dynamic programming method should come to your mind naturally.”-----看到字符串操作,首先应该想到DP算法。
大体思路是,s1取一部分s2取一部分,最后是否能匹配s3。
动态规划数组是dp[i][j],表示: s1取前i位(但是第i为之前的字符串也必须是构成s3的),s2取前j位(但是第J位之前的字符串也必须是构成s3的),是否能组成s3的前i+j位。
初始化是,假设s1为空,那么s2每一位跟s3匹配放入dp[0][j];假设s2为空,那么s1每一位跟s3匹配放入dp[i][0]。
相似题目:
s1, s2只有两个字符串,因此可以展平为一个二维地图,判断是否能从左上角走到右下角。
当s1到达第i个元素,s2到达第j个元素:
地图上往右一步就是s2[j-1]匹配s3[i+j-1]。
地图上往下一步就是s1[i-1]匹配s3[i+j-1]。
示例:s1="aa",s2="ab",s3="aaba"。标1的为可行。最终返回右下角。
矩阵中红色的数值1表示dp[s1==0][s2==1]是构成s3的,所以1表示true.
0 a b
0 1 1 0
a 1 1 1
a 1 0 1
这个数组就是dp[i][j]的取值
class Solution { public: /** * Determine whether s3 is formed by interleaving of s1 and s2. * @param s1, s2, s3: As description. * @return: true of false. */ bool isInterleave(string s1, string s2, string s3) { // write your code here if(s3.length()!=s1.length()+s2.length()) return false; if(s1.length()==0) return s2==s3; if(s2.length()==0) return s1==s3; vector<vector<bool> > dp(s1.length()+1,vector<bool>(s2.length()+1,false)); dp[0][0] = true; for(int i=1;i<=s1.length();i++) dp[i][0] = dp[i-1][0]&&(s3[i-1]==s1[i-1]); for(int i=1;i<=s2.length();i++) dp[0][i] = dp[0][i-1]&&(s3[i-1]==s2[i-1]); for(int i=1;i<=s1.length();i++) { for(int j=1;j<=s2.length();j++) { int t = i+j; if(s1[i-1]==s3[t-1]) dp[i][j] = dp[i][j]||dp[i-1][j]; if(s2[j-1]==s3[t-1]) dp[i][j] = dp[i][j]||dp[i][j-1]; } } return dp[s1.length()][s2.length()]; } };