Interleaving String
Given s1, s2, s3, 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.
首先考虑的是用栈记录匹配的状态,代码如下,会超时
1 public boolean isInterleave(String s1, String s2, String s3) { 2 if(s1.length()+s2.length()!=s3.length()){ 3 return false; 4 } 5 Stack<Integer> stack1 = new Stack<Integer>(); 6 Stack<Integer> stack2 = new Stack<Integer>(); 7 stack1.push(-1); 8 stack2.push(-1); 9 while(!stack1.empty()){ 10 int index1 = stack1.pop(); 11 int index2 = stack2.pop(); 12 if(index1+index2+2==s3.length()){ 13 return true; 14 } 15 if(index1+1<s1.length()&&s1.charAt(index1+1)==s3.charAt(index1+index2+2)){ 16 stack1.push(index1+1); 17 stack2.push(index2); 18 } 19 if(index2+1<s2.length()&&s2.charAt(index2+1)==s3.charAt(index1+index2+2)){ 20 stack1.push(index1); 21 stack2.push(index2+1); 22 } 23 } 24 return false; 25 }
然后想了想之前做过的题,考虑使用动态规划,设grid[i][j][k]表示s1.substring(0,i)和s2.substring(0,j)与s3.substring(0,k)是否是interleaving string,因此可得出状态方程
grid[i][j][k] = (s1.charAt(i-1) == s3.charAt(k-1) && grid[i-1][j][k-1]) || (s2.charAt(j-1) == s3.charAt(k-1) && grid[i][j-1][k-1])
代码如下:
1 public boolean isInterleave(String s1, String s2, String s3) { 2 boolean grid[][][] = new boolean[s1.length()+1][s2.length()+1][s3.length()+1]; 3 if(s1.length()+s2.length()!=s3.length()){ 4 return false; 5 } 6 if(s1.equals("")){ 7 return s2.equals(s3); 8 }else if(s2.equals("")){ 9 return s1.equals(s3); 10 } 11 grid[0][0][0] = true; 12 for(int i = 1;i<=s1.length();i++){ 13 grid[i][0][i] = s1.charAt(i-1)==s3.charAt(i-1)&&grid[i-1][0][i-1]; 14 } 15 for(int i = 1;i<=s2.length();i++){ 16 grid[0][i][i] = s2.charAt(i-1)==s3.charAt(i-1)&&grid[0][i-1][i-1]; 17 } 18 for(int i=1;i<=s1.length();i++){ 19 for(int j=1;j<=s2.length();j++){ 20 for(int k=1;k<=s3.length();k++){ 21 grid[i][j][k] = (s1.charAt(i-1)==s3.charAt(k-1)&&grid[i-1][j][k-1])||(s2.charAt(j-1)==s3.charAt(k-1)&&grid[i][j-1][k-1]); 22 } 23 } 24 } 25 return grid[s1.length()][s2.length()][s3.length()]; 26 }
AC 748ms
继续思考,由于k!=i+j时grid[i][j][k]的值一定是false,因此这种情况没有意义,因此可以将k用i和j表示,这样就可以降维,将grid降维二阶矩阵。代码如下
1 public boolean isInterleave(String s1, String s2, String s3) { 2 boolean grid[][] = new boolean[s1.length()+1][s2.length()+1]; 3 if(s1.length()+s2.length()!=s3.length()){ 4 return false; 5 } 6 if(s1.equals("")){ 7 return s2.equals(s3); 8 }else if(s2.equals("")){ 9 return s1.equals(s3); 10 } 11 grid[0][0] = true; 12 for(int i = 1;i<=s1.length();i++){ 13 grid[i][0] = s1.charAt(i-1)==s3.charAt(i-1)&&grid[i-1][0]; 14 } 15 for(int i = 1;i<=s2.length();i++){ 16 grid[0][i] = s2.charAt(i-1)==s3.charAt(i-1)&&grid[0][i-1]; 17 } 18 for(int i=1;i<=s1.length();i++){ 19 for(int j=1;j<=s2.length();j++){ 20 for(int k=1;k<=s3.length();k++){ 21 grid[i][j] = (s1.charAt(i-1)==s3.charAt(i+j-1)&&grid[i-1][j])||(s2.charAt(j-1)==s3.charAt(i+j-1)&&grid[i][j-1]); 22 } 23 } 24 } 25 return grid[s1.length()][s2.length()]; 26 }
AC 660ms