Tag Archives: c++

[LeetCode] 291. Word Pattern II

Given apatternand a stringstr, find ifstrfollows the same pattern.

Herefollowmeans a full match, such that there is a bijection between a letter inpatternand anon-emptysubstring instr.

Examples:

pattern ="abab", str ="redblueredblue"should return true.

pattern ="aaaa", str ="asdasdasdasd"should return true.

pattern ="aabb", str ="xyzabcxzyabc"should return false.

Notes:
You may assume bothpatternandstrcontains only lowercase letters.

290. Word pattern is an extension of word pattern. The difference is that there are no spaces in the word string, so we can’t split the words directly by spaces.

You can use the backtracking method to judge each case, use the hash table to establish the mapping between pattern characters and words, and use the variables p and R to record the position of the current recursive pattern characters and word strings. In the recursive function, if P and R are equal to the length of the pattern string and single word string respectively, it means that the matching is completed successfully, and return to ture. Otherwise, if a If the match is reached and the other one is not, it means that the match failed and returns false.

Solution: backtracking

Python:

# Time:  O(n * C(n - 1, c - 1)), n is length of str, c is unique count of pattern,
#                                there are H(n - c, c - 1) = C(n - 1, c - 1) possible splits of string,
#                                and each one costs O(n) to check if it matches the word pattern.
# Space: O(n + c)

class Solution(object):
    def wordPatternMatch(self, pattern, str):
        """
        :type pattern: str
        :type str: str
        :rtype: bool
        """
        w2p, p2w = {}, {}
        return self.match(pattern, str, 0, 0, w2p, p2w)


    def match(self, pattern, str, i, j, w2p, p2w):
        is_match = False
        if i == len(pattern) and j == len(str):
            is_match = True
        elif i < len(pattern) and j < len(str):
            p = pattern[i]
            if p in p2w:
                w = p2w[p]
                if w == str[j:j+len(w)]:  # Match pattern.
                    is_match = self.match(pattern, str, i + 1, j + len(w), w2p, p2w)
                # Else return false.
            else:
                for k in xrange(j, len(str)):  # Try any possible word
                    w = str[j:k+1]
                    if w not in w2p:
                        # Build mapping. Space: O(n + c)
                        w2p[w], p2w[p] = p, w;
                        is_match = self.match(pattern, str, i + 1, k + 1, w2p, p2w)
                        w2p.pop(w), p2w.pop(p);
                    if is_match:
                        break
        return is_match  

C++:

class Solution {
public:
    bool wordPatternMatch(string pattern, string str) {
        unordered_map<char, string> m;
        return helper(pattern, 0, str, 0, m);
    }
    bool helper(string pattern, int p, string str, int r, unordered_map<char, string&> &m) {
        if (p == pattern.size() && r == str.size()) return true;
        if (p == pattern.size() || r == str.size()) return false;
        char c = pattern[p];
        for (int i = r; i < str.size(); ++i) {
            string t = str.substr(r, i - r + 1);
            if (m.count(c) && m[c] == t) {
                if (helper(pattern, p + 1, str, i + 1, m)) return true;
            } else if (!m.count(c)) {
                bool b = false;
                for (auto it : m) {
                    if (it.second == t) b = true;
                } 
                if (!b) {
                    m[c] = t;
                    if (helper(pattern, p + 1, str, i + 1, m)) return true;
                    m.erase(c);
                }
            }
        }
        return false;
    }
};  

C++:

class Solution {
public:
    bool wordPatternMatch(string pattern, string str) {
        unordered_map<char, string> m;
        set<string> s;
        return helper(pattern, 0, str, 0, m, s);
    }
    bool helper(string pattern, int p, string str, int r, unordered_map<char, string> &m, set<string&> &s) {
        if (p == pattern.size() && r == str.size()) return true;
        if (p == pattern.size() || r == str.size()) return false;
        char c = pattern[p];
        for (int i = r; i < str.size(); ++i) {
            string t = str.substr(r, i - r + 1);
            if (m.count(c) && m[c] == t) {
                if (helper(pattern, p + 1, str, i + 1, m, s)) return true;
            } else if (!m.count(c)) {
                if (s.count(t)) continue;
                m[c] = t;
                s.insert(t);
                if (helper(pattern, p + 1, str, i + 1, m, s)) return true;
                m.erase(c);
                s.erase(t);
            }
        }
        return false;
    }
};

Using the Xtreme Toolkit Pro toolbar

Xtreme Toolkit Pro is the most comprehensive interface control package in MFC development. It provides 11 mainstream Visual C + + MFC controls needed for Windows development, including command bars, controls, chart pro, calendar, docking panel, property grid, report control, shortcut bar, syntax edit, skin framework and task panel. If you are interested in the product, please go to Huidu to download the latest trial version of Xtreme Toolkit Pro ! Click to get more free Xtreme Toolkit Pro tutorials, videos and examples

There are many articles about docking toolbars. But I think it’s important to find the same information on Microsoft’s MSDN site. In short

Add the following methods to your CMainFrame class:

void CMainFrame::DockControlBarLeftOf(
                        CToolBar* Bar, CToolBar* LeftOf)
{
    CRect rect;
    DWORD dw;
    UINT n;

    // get MFC to adjust the dimensions of all docked ToolBars
    // so that GetWindowRect will be accurate
    RecalcLayout(TRUE);

    LeftOf-&>GetWindowRect(&rect);
    rect.OffsetRect(1,0);
    dw=LeftOf-&>GetBarStyle();
    n = 0;
    n = (dw&CBRS_ALIGN_TOP) ?AFX_IDW_DOCKBAR_TOP : n;
    n = (dw&CBRS_ALIGN_BOTTOM && n==0) ?
                                AFX_IDW_DOCKBAR_BOTTOM : n;
    n = (dw&CBRS_ALIGN_LEFT && n==0) ?
                                AFX_IDW_DOCKBAR_LEFT : n;
    n = (dw&CBRS_ALIGN_RIGHT && n==0) ?
                                AFX_IDW_DOCKBAR_RIGHT : n;

    // When we take the default parameters on rect, DockControlBar
    // will dock each Toolbar on a seperate line. By calculating a
    // rectangle, we are simulating a Toolbar being dragged to that
    // location and docked.
    DockControlBar(Bar,n,&rect);
}

Now, instead of using dockcontrolbar in your CMainFrame:: oncreate, use dockcontrolbar leftof:

m_wndToolBar1.EnableDocking(CBRS_ALIGN_ANY);
m_wndToolBar2.EnableDocking(CBRS_ALIGN_ANY);
EnableDocking(CBRS_ALIGN_ANY);
DockControlBar(&m_wndToolBar1);
DockControlBarLeftOf(&m_wndToolBar2,&m_wndToolBar1);

This will stop M_ M on the left side of wndtoolbar1_ wndToolBar2。 Click to get the demo corresponding to the article.

That’s all for today, download the latest version of Xtreme Toolkit Pro and share your thoughts on the product in the comments area below. Your feedback can help us find the right direction in the future update!