Problem p01756 (C++) — buggy submission, verdict: Memory Limit Exceeded

#include <bits/stdc++.h>
using namespace std;

typedef pair<string, string> PS;

#define fi first
#define se second
#define repl(i, a, b) for (int i = (int)(a); i < (int)(b); i++)
#define rep(i, n) repl(i, 0, n)
#define all(x) (x).begin(), (x).end()
#define dbg(x) cout << #x "=" << x << endl
#define mmax(x, y) (x > y ? x : y)
#define mmin(x, y) (x < y ? x : y)
#define maxch(x, y) x = mmax(x, y)
#define minch(x, y) x = mmin(x, y)
#define uni(x) x.erase(unique(all(x)), x.end())
#define exist(x, y) (find(all(x), y) != x.end())
#define bcnt __builtin_popcount

#define INF INT_MAX / 3
#define mod 1000000007

class PMA {
  PMA *next[27];
  vector<int> matched;

  PMA() { rep(i, 27) next[i] = NULL; }

  void build(vector<string> &sp) {
    vector<vector<int>> p;
    rep(i, sp.size()) {
      p.push_back(vector<int>());
      rep(j, sp[i].size()) p[p.size() - 1].push_back((int)(sp[i][j] - 'a' + 1));
    }
    rep(i, 27) next[i] = NULL;
    this->next[0] = this;
    rep(i, p.size()) {
      PMA *now = this;
      rep(j, p[i].size()) {
        if (now->next[p[i][j]] == 0)
          now->next[p[i][j]] = new PMA;
        now = now->next[p[i][j]];
      }
      now->matched.push_back(i);
    }

    queue<PMA *> q;
    repl(i, 1, 27) {
      if (!this->next[i])
        this->next[i] = this;
      else {
        this->next[i]->next[0] = this;
        q.push(this->next[i]);
      }
    }

    while (!q.empty()) {
      PMA *now = q.front();
      q.pop();
      repl(i, 1, 27) if (now->next[i]) {
        PMA *nxt = now->next[0];
        while (!nxt->next[i])
          nxt = nxt->next[0];
        now->next[i]->next[0] = nxt->next[i];
        vector<int> &m1 = now->next[i]->matched, &m2 = nxt->next[i]->matched;
        rep(j, m2.size()) if (!binary_search(m1.begin(), m1.end(), m2[j]))
            m1.push_back(m2[j]);
        sort(m1.begin(), m1.end());
        q.push(now->next[i]);
      }
    }
  }

public:
  /* initialized by C-array of pattern string */
  PMA(string *parray, int n) {
    vector<string> p;
    rep(i, n) p.push_back(parray[i]);
    build(p);
  }

  /* initialized by vector of pattern string */
  PMA(vector<string> p) { build(p); }

  /* find all substring mathing pattern */
  vector<vector<int>> match(string ss) {
    vector<int> s;
    rep(i, ss.size()) s.push_back(ss[i] - 'a' + 1);
    vector<vector<int>> idx(s.size());
    PMA *pma = this;
    rep(i, s.size()) {
      while (!pma->next[s[i]])
        pma = pma->next[0];
      pma = pma->next[s[i]];
      for (int j : pma->matched)
        idx[i].push_back(j);
    }
    return idx;
  }
};

string S;
int Q;
vector<PS> qs;
unordered_map<string, int> sidx;
vector<string> ss;
int idx = 0;

int main() {
  cin >> S;
  cin >> Q;
  rep(i, Q) {
    string a, b;
    cin >> a >> b;
    qs.push_back(PS(a, b));
    if (sidx.find(a) == sidx.end()) {
      sidx[a] = idx++;
      ss.push_back(a);
    }
    if (sidx.find(b) == sidx.end()) {
      sidx[b] = idx++;
      ss.push_back(b);
    }
  }
  PMA pma(ss);

  vector<vector<int>> idxs = pma.match(S);
  vector<int> l(ss.size(), INF), r(ss.size(), -INF);
  rep(i, idxs.size()) {
    for (int j : idxs[i]) {
      int midx = i - ss[j].size() + 1;
      minch(l[j], midx);
      maxch(r[j], midx);
    }
  }

  rep(i, qs.size()) {
    int ai = sidx[qs[i].fi];
    int bi = sidx[qs[i].se];
    if (l[ai] != INF && r[bi] != -INF &&
        (l[ai] + ss[ai].size() - 1) <= (r[bi] + ss[bi].size() - 1)) {
      cout << r[bi] - l[ai] + ss[bi].size() << endl;
    } else {
      cout << 0 << endl;
    }
  }

  return 0;
}


Error: MLE

Fixed submission:

#include <bits/stdc++.h>
using namespace std;

typedef pair<string, string> PS;

#define fi first
#define se second
#define repl(i, a, b) for (int i = (int)(a); i < (int)(b); i++)
#define rep(i, n) repl(i, 0, n)
#define all(x) (x).begin(), (x).end()
#define dbg(x) cout << #x "=" << x << endl
#define mmax(x, y) (x > y ? x : y)
#define mmin(x, y) (x < y ? x : y)
#define maxch(x, y) x = mmax(x, y)
#define minch(x, y) x = mmin(x, y)
#define uni(x) x.erase(unique(all(x)), x.end())
#define exist(x, y) (find(all(x), y) != x.end())
#define bcnt __builtin_popcount

#define INF INT_MAX / 3
#define mod 1000000007

class PMA {
  PMA *next[256];
  vector<int> matched;

  PMA() { rep(i, 256) next[i] = NULL; }

  void build(vector<string> &p) {
    rep(i, 256) next[i] = NULL;
    this->next[0] = this;
    rep(i, p.size()) {
      PMA *now = this;
      rep(j, p[i].length()) {
        if (now->next[p[i][j]] == 0)
          now->next[p[i][j]] = new PMA;
        now = now->next[p[i][j]];
      }
      now->matched.push_back(i);
    }

    queue<PMA *> q;
    repl(i, 1, 256) {
      if (!this->next[i])
        this->next[i] = this;
      else {
        this->next[i]->next[0] = this;
        q.push(this->next[i]);
      }
    }

    while (!q.empty()) {
      PMA *now = q.front();
      q.pop();
      repl(i, 1, 256) if (now->next[i]) {
        PMA *nxt = now->next[0];
        while (!nxt->next[i])
          nxt = nxt->next[0];
        now->next[i]->next[0] = nxt->next[i];
        vector<int> &m1 = now->next[i]->matched, &m2 = nxt->next[i]->matched;
        rep(j, m2.size()) if (!binary_search(m1.begin(), m1.end(), m2[j]))
            m1.push_back(m2[j]);
        sort(m1.begin(), m1.end());
        q.push(now->next[i]);
      }
    }
  }

public:
  /* initialized by C-array of pattern string */
  PMA(string *parray, int n) {
    vector<string> p;
    rep(i, n) p.push_back(parray[i]);
    build(p);
  }

  /* initialized by vector of pattern string */
  PMA(vector<string> p) { build(p); }

  /* find all substring mathing pattern */
  vector<vector<int>> match(string s) {
    vector<vector<int>> idx(s.length());
    PMA *pma = this;
    rep(i, s.length()) {
      while (!pma->next[s[i]])
        pma = pma->next[0];
      pma = pma->next[s[i]];
      for (int j : pma->matched)
        idx[i].push_back(j);
    }
    return idx;
  }
};

string S;
int Q;
vector<PS> qs;
unordered_map<string, int> sidx;
vector<string> ss;
int idx = 0;

int main() {
  cin >> S;
  cin >> Q;
  rep(i, Q) {
    string a, b;
    cin >> a >> b;
    qs.push_back(PS(a, b));
    if (sidx.find(a) == sidx.end()) {
      sidx[a] = idx++;
      ss.push_back(a);
    }
    if (sidx.find(b) == sidx.end()) {
      sidx[b] = idx++;
      ss.push_back(b);
    }
  }
  PMA pma(ss);

  vector<vector<int>> idxs = pma.match(S);
  vector<int> l(ss.size(), INF), r(ss.size(), -INF);
  rep(i, idxs.size()) {
    for (int j : idxs[i]) {
      int midx = i - ss[j].size() + 1;
      minch(l[j], midx);
      maxch(r[j], midx);
    }
  }

  rep(i, qs.size()) {
    int ai = sidx[qs[i].fi];
    int bi = sidx[qs[i].se];
    if (l[ai] != INF && r[bi] != -INF &&
        (l[ai] + ss[ai].size() - 1) <= (r[bi] + ss[bi].size() - 1)) {
      cout << r[bi] - l[ai] + ss[bi].size() << endl;
    } else {
      cout << 0 << endl;
    }
  }

  return 0;
}