程序媛詹妮弗
终身学习

Given a string s1, we may represent it as a binary tree by partitioning it to two non-empty substrings recursively.

Below is one possible representation of s1 = "great":

 great
   /    \
  gr    eat
 / \    /  \
g   r  e   at
           / \
          a   t

To scramble the string, we may choose any non-leaf node and swap its two children.

For example, if we choose the node "gr" and swap its two children, it produces a scrambled string "rgeat".

   rgeat
   /    \
  rg    eat
 / \    /  \
r   g  e   at
           / \
          a   t

 

题意:

对于一个字符串,若通过一些列树形颠倒(确定一点后,前后子串交换)得到一个新的字符串,则互为Scramble String

 

思路:

这道题面试很低频,因为若要dp解,则需三维dp,难度很高不适合面试

直接用递归,观察规律:

若s1 和 s2 长度都为1 : 两字符串必须完全相当

若s1 和 s2 长度都为2: 则当s1 = "ab"时, s2 = "ab" || "ba"

若s1 和 s2 长度都为3: 将 s1 分成 s1Left 和 s1Right两部分

                                    s2 分成 s2Left 和 s2Right 两部分

                                  则 ( s1Left  isScrambled s2Left  && s1Right isScrambled s2Right ) 或者  (s1Left  isScrambled s2Right && s1Right isScrambled s2Left  ) 

如图,

 

所以,

先判断s1和s2是否是valid anagram (变位词): 意味着两个字符串长度一致,互相只是各个字符串变换了位置

再递归生成s1的左边、右边,s2 的左边、右边

递归出口: s1等于s2 return true

 

代码:

 1 class Solution {
 2     public boolean isScramble(String s1, String s2) {
 3          // corner
 4         if(s1.length() != s2.length() || s1 == null || s2 == null) return false;
 5         // recursion 出口
 6         if(s1.equals(s2)) return true; // 一定要加,否则recursion 没有出口
 7         // valid anagram or not 
 8         int[]map = new int[256];
 9         for(int i = 0; i < s1.length(); i++){
10             map[s1.charAt(i)] ++;
11             map[s2.charAt(i)] --;
12         } 
13         for(int i : map){
14             if( i != 0){
15                 return false;
16             }
17         }
18         // recursion 
19         for(int i = 1; i < s1.length(); i++){ 
20         if(isScramble(s1.substring(0,i), s2.substring(0,i)) && isScramble(s1.substring(i), s2.substring(i))) return true;
21         if(isScramble(s1.substring(0,i), s2.substring(s2.length()-i)) && isScramble(s1.substring(i), s2.substring(0, s2.length()-i))) return true;
22               
23         } 
24        return false;
25     }
26     
27 }

 

posted on 2018-05-18 03:03  程序媛詹妮弗  阅读(127)  评论(0编辑  收藏  举报