leetcode:87. Scramble String

在这里插入图片描述

仅一步之遥就自己做出这道hard了:(

首先自己观察对于每个子问题都是一样的逻辑,所以适合用递归:

class Solution {
public:
    bool isScramble(string s1, string s2) {
        int sz1 = s1.size(), sz2 = s2.size();
        if (sz1 != sz2)
            return false;
        return helper(s1, s2, 0, sz1-1, 0, sz2-1);
    }
private:
    bool helper(string& s1, string& s2, int l1, int r1, int l2, int r2) {
        if (l1 == r1) {
            if (s1[l1] == s2[l2])
                return true;
            else 
                return false;
        }
        for (int i = 1; i <= (r1 - l1); ++i) {
            if (helper(s1, s2, l1, l1+i-1, l2, l2+i-1) && helper(s1, s2, l1+i, r1, l2+i, r2))
                return true;
            if (helper(s1, s2, l1, l1+i-1, r2-i+1, r2) && helper(s1, s2, l1+i, r1, l2, r2-i))
                return true;
        }
        return false;
    }
};

结果超时。
然后看了评论区,才发现忘了把中间结果保存:

class Solution {
public:
    bool isScramble(string s1, string s2) {
        int sz1 = s1.size(), sz2 = s2.size();
        if (sz1 != sz2)
            return false;
        return helper(s1, s2, 0, sz1-1, 0, sz2-1);
    }
private:
    map<pair<pair<int, int>, pair<int, int>>, bool> m;//unordered_map不能用,需要自己提供hash函数。
    bool helper(string& s1, string& s2, int l1, int r1, int l2, int r2) {
        if (l1 == r1) {
            if (s1[l1] == s2[l2])
                return true;
            else 
                return false;
        }
        auto key = make_pair(make_pair(l1, r1), make_pair(l2, r2));
        if (m.find(key) != m.end())
            return m[key];
        for (int i = 1; i <= (r1 - l1); ++i) {
            if (helper(s1, s2, l1, l1+i-1, l2, l2+i-1) && helper(s1, s2, l1+i, r1, l2+i, r2) ||
               helper(s1, s2, l1, l1+i-1, r2-i+1, r2) && helper(s1, s2, l1+i, r1, l2, r2-i)) {
                m[key] = true;
                return true;
            }
        }
        m[key] = false;
        return false;
    }
};

//1.没有想到对中间结果进行缓存,是一大失误。
//2.从顶向下的编码确实更加符合思考的逻辑。

DP的核心思想是保存子问题的解,不用重复解答。这里忘记了这一点,导致没有pass
这里的状态是:对于s1[l1:r1]和s2[l2:r2]来说,是不是scramble的?

这题其实就是top-down+memo,只是一开始没想到这一点,忘了memo

posted @ 2019-09-11 16:49  于老师的父亲王老爷子  阅读(17)  评论(0)    收藏  举报