leecode 解题总结:87. Scramble String

来源:互联网 发布:mac爱奇艺 编辑:程序博客网 时间:2024/05/17 01:23
#include <iostream>#include <stdio.h>#include <vector>#include <unordered_map>#include <string>using namespace std;/*问题: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   tTo 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   tWe say that "rgeat" is a scrambled string of "great".Similarly, if we continue to swap the children of nodes "eat" and "at", it produces a scrambled string "rgtae".    rgtae   /    \  rg    tae / \    /  \r   g  ta  e       / \      t   aWe say that "rgtae" is a scrambled string of "great".Given two strings s1 and s2 of the same length, determine if s2 is a scrambled string of s1.分析:确定一种操作交换非叶子节点,然后交换其孩子节点,最后遍历所有叶子节点得到新生成的字符串。现在判定字符串是否是由另一个字符串进行交换操作得到的。难点在于由字符串构建二叉树时,由于每次是将当前字符串分割为两个非空字符串来建树的,因此如何分割,可能会对其子串进行交换操作产生影响。暴力破解:对原始字符串尝试进行每一种分割,然后建立二叉树,对每一颗二叉树的任意非叶子节点或者多个非叶子节点进行交换操作,然后对于每一种操作遍历所有叶子节点,得到交换字符串,和当前给定字符串比较,看是否相等。这个时间复杂度太大。一般应该跟树相关用递归。比较两个字符串,如果当前字符相同。想不到。输入:rgeat greatrgtae greattearg great输出:truetruefalse关键:1 leecode答案:题目中存在一个关键点就是进行交换操作后,比较两个字符串是否是经过该种操作可以比较s1[1...k] 和s2[1,,,k] , 以及s1[k+1..len1]和s2[k+1..len2]或者比较s1[1...k] 和s2[len2-k+1,,,len2] ,以及s1[k+1..len1]和s2[1..k]并用哈希map记录s1+s2的结果2//记忆化搜索,如果s1 + s2存在就返回1,否则返回0if(result.count(s1 + s2)){return result[s1 + s2];} */class Solution {public:bool isScramble(string s1 , string s2 , unordered_map<string , bool>& result){if(s1.empty() && s2.empty()){return true;}int len = s1.length();bool isOk = false;//记忆化搜索,如果s1 + s2存在就返回1,否则返回0if(result.count(s1 + s2)){return result[s1 + s2];}//只剩两个字符if(1 == len){isOk = s1.at(0) == s2.at(0) ? true : false;}//多个字符,需要先划分,然后递归处理else{for(int i = 1 ; i <= len - 1; i++){isOk = isScramble(s1.substr(0 ,i) , s2.substr(0 ,i) , result) && isScramble(s1.substr(i , len - i) , s2.substr(i , len - i) , result);if(isOk){break;}    //截取字符串需要指定起始位置substr(0 , i) , s2.substr(len - i , i)isOk = isScramble(s1.substr(0 , i) , s2.substr(len - i , i) , result) && isScramble(s1.substr(i , len - i) , s2.substr(0 ,len - i) , result);if(isOk){break;}}}result[s1 + s2] = isOk;return isOk;}    bool isScramble(string s1, string s2) {unordered_map<string , bool> result;bool isOk = isScramble(s1 , s2 , result);return isOk;    }};void process(){ string s1; string s2; Solution solution; while(cin >> s1 >> s2 ) { bool result = solution.isScramble(s1 , s2); if(result) { cout << "true" << endl; } else { cout << "false" << endl; } }}int main(int argc , char* argv[]){process();getchar();return 0;}

0 0
原创粉丝点击