Problem p00598 (C++) — buggy submission, verdict: Time Limit Exceeded

#include <algorithm>
#include <iostream>
#include <iterator>
#include <map>
#include <set>
#include <string>
#include <vector>
using namespace std;

#define State string::const_iterator

class ParseError {};

map<char, vector<int>> sets;

vector<int> expression(State &begin);
vector<int> term(State &begin);
vector<int> _set(State &begin);
vector<int> factor(State &begin);
inline void consume(State &begin, char expected);

void compress(vector<int> &v) {
  sort(v.begin(), v.end());
  v.erase(unique(v.begin(), v.end()), v.end());
}

vector<int> D(vector<int> my_left, vector<int> my_right) {
  vector<int> ret = {};
  std::set_difference(my_left.begin(), my_left.end(), my_right.begin(),
                      my_right.end(), back_inserter(ret));
  return ret;
}

vector<int> I(vector<int> my_left, vector<int> my_right) {
  vector<int> ret = {};
  set_intersection(std::begin(my_left), std::end(my_left), std::begin(my_right),
                   std::end(my_right), back_inserter(ret));

  return ret;
}

vector<int> U(vector<int> my_left, vector<int> my_right) {
  vector<int> ret = {};
  set_union(std::begin(my_left), std::end(my_left), std::begin(my_right),
            std::end(my_right), back_inserter(ret));

  return ret;
}

vector<int> S(vector<int> my_left, vector<int> my_right) {
  vector<int> ret = {};
  set_symmetric_difference(std::begin(my_left), std::end(my_left),
                           std::begin(my_right), std::end(my_right),
                           back_inserter(ret));

  return ret;
}

vector<int> C(vector<int> v) {
  vector<int> ret = {};
  std::set_difference(sets['U'].begin(), sets['U'].end(), v.begin(), v.end(),
                      back_inserter(ret));
  return ret;
}

// 四則演算の式をパースして、その評価結果を返す。
vector<int> expression(State &begin) {
  vector<int> ret = term(begin);

  while (true) {
    if (*begin == 'u') {
      consume(begin, 'u');
      ret = U(ret, term(begin));
    } else if (*begin == 'i') {
      consume(begin, 'i');
      ret = I(ret, term(begin));
    } else if (*begin == 'd') {
      consume(begin, 'd');
      ret = D(ret, term(begin));
    } else if (*begin == 's') {
      consume(begin, 's');
      ret = S(ret, term(begin));
    } else {
      break;
    }
  }

  return ret;
}

// 乗算除算の式をパースして、その評価結果を返す。
vector<int> term(State &begin) {

  /*
  vector<int> ret = {};
  if(*begin == 'c'){
      consume(begin, 'c');
      vector<int> v = factor(begin);
      sort(v.begin(), v.end());
      ret = D(sets['U'], v);
  }
  else {
      ret = factor(begin);
  }

  return ret;
  */
  if (*begin == 'c') {
    consume(begin, 'c');
    return C(factor(begin));
  } else {
    return factor(begin);
  }
}

// 括弧か数をパースして、その評価結果を返す。
vector<int> factor(State &begin) {
  if (*begin == '(') {
    consume(begin, '('); // '('を飛ばす。
    vector<int> ret = expression(begin);
    consume(begin, ')'); // ')'を飛ばす。
    return ret;
  } else {
    /*
    vector<int> ret = sets[*begin];
    sort(ret.begin(), ret.end());
    begin++;
    return ret;
     */
    return sets[*begin++];
  }
}

// beginがexpectedを指していたらbeginを一つ進める。
inline void consume(State &begin, char expected) {
  if (*begin == expected) {
    begin++;
  } else {
    cerr << "Expected '" << expected << "' but got '" << *begin << "'" << endl;
    cerr << "Rest string is '";
    while (*begin) {
      cerr << *begin++;
    }
    cerr << "'" << endl;
    throw ParseError();
  }
}

int main() {

  while (true) {

    sets.clear();

    char se;
    int n;

    while (cin >> se >> n) {

      if (se == 'R') {
        break;
      } else {
        for (int i = 0; i < n; i++) {
          int input;
          cin >> input;
          sets[se].push_back(input);
          sets['U'].push_back(input);
        }
      }
    }

    if (sets['U'].size() == 0) {
      break;
    }

    for (auto &itr : sets) {
      sort(itr.second.begin(), itr.second.end());
    }

    // 重複削除
    compress(sets['U']);

    cin.ignore();
    string formula;
    getline(cin, formula);

    if (formula == "shutdown") {
      break;
    }

    State begin = formula.begin();

    vector<int> ans = expression(begin);

    if (ans.empty()) {
      cout << "NULL" << endl;
    } else {
      cout << ans[0];

      for (int i = 1; i < ans.size(); i++) {
        cout << " " << ans[i];
      }

      cout << endl;
    }
  }

  return 0;
}


Error: TLE

Fixed submission:

#include <algorithm>
#include <iostream>
#include <iterator>
#include <map>
#include <set>
#include <string>
#include <vector>
using namespace std;

#define State string::const_iterator

class ParseError {};

map<char, vector<int>> sets;

vector<int> expression(State &begin);
vector<int> term(State &begin);
vector<int> _set(State &begin);
vector<int> factor(State &begin);
inline void consume(State &begin, char expected);

void compress(vector<int> &v) {
  sort(v.begin(), v.end());
  v.erase(unique(v.begin(), v.end()), v.end());
}

vector<int> D(vector<int> my_left, vector<int> my_right) {
  vector<int> ret = {};
  std::set_difference(my_left.begin(), my_left.end(), my_right.begin(),
                      my_right.end(), back_inserter(ret));
  return ret;
}

vector<int> I(vector<int> my_left, vector<int> my_right) {
  vector<int> ret = {};
  set_intersection(std::begin(my_left), std::end(my_left), std::begin(my_right),
                   std::end(my_right), back_inserter(ret));

  return ret;
}

vector<int> U(vector<int> my_left, vector<int> my_right) {
  vector<int> ret = {};
  set_union(std::begin(my_left), std::end(my_left), std::begin(my_right),
            std::end(my_right), back_inserter(ret));

  return ret;
}

vector<int> S(vector<int> my_left, vector<int> my_right) {
  vector<int> ret = {};
  set_symmetric_difference(std::begin(my_left), std::end(my_left),
                           std::begin(my_right), std::end(my_right),
                           back_inserter(ret));

  return ret;
}

vector<int> C(vector<int> v) {
  vector<int> ret = {};
  std::set_difference(sets['U'].begin(), sets['U'].end(), v.begin(), v.end(),
                      back_inserter(ret));
  return ret;
}

// 四則演算の式をパースして、その評価結果を返す。
vector<int> expression(State &begin) {
  vector<int> ret = term(begin);

  while (true) {
    if (*begin == 'u') {
      consume(begin, 'u');
      ret = U(ret, term(begin));
    } else if (*begin == 'i') {
      consume(begin, 'i');
      ret = I(ret, term(begin));
    } else if (*begin == 'd') {
      consume(begin, 'd');
      ret = D(ret, term(begin));
    } else if (*begin == 's') {
      consume(begin, 's');
      ret = S(ret, term(begin));
    } else {
      break;
    }
  }

  return ret;
}

// 乗算除算の式をパースして、その評価結果を返す。
vector<int> term(State &begin) {

  /*
  vector<int> ret = {};
  if(*begin == 'c'){
      consume(begin, 'c');
      vector<int> v = factor(begin);
      sort(v.begin(), v.end());
      ret = D(sets['U'], v);
  }
  else {
      ret = factor(begin);
  }

  return ret;
  */
  if (*begin == 'c') {
    consume(begin, 'c');
    return C(factor(begin));
  } else {
    return factor(begin);
  }
}

// 括弧か数をパースして、その評価結果を返す。
vector<int> factor(State &begin) {
  if (*begin == '(') {
    consume(begin, '('); // '('を飛ばす。
    vector<int> ret = expression(begin);
    consume(begin, ')'); // ')'を飛ばす。
    return ret;
  } else {
    /*
    vector<int> ret = sets[*begin];
    sort(ret.begin(), ret.end());
    begin++;
    return ret;
     */
    return sets[*begin++];
  }
}

// beginがexpectedを指していたらbeginを一つ進める。
inline void consume(State &begin, char expected) {
  if (*begin == expected) {
    begin++;
  } else {
    cerr << "Expected '" << expected << "' but got '" << *begin << "'" << endl;
    cerr << "Rest string is '";
    while (*begin) {
      cerr << *begin++;
    }
    cerr << "'" << endl;
    throw ParseError();
  }
}

int main() {

  while (true) {

    sets.clear();

    while (true) {

      char se;
      int n;

      cin >> se >> n;

      if (se == 'R') {
        break;
      } else {
        for (int i = 0; i < n; i++) {
          int input;
          cin >> input;
          sets[se].push_back(input);
          sets['U'].push_back(input);
        }
      }
    }

    for (auto &itr : sets) {
      sort(itr.second.begin(), itr.second.end());
    }

    // 重複削除
    compress(sets['U']);

    cin.ignore();
    string formula;
    getline(cin, formula);

    if (formula == "shutdown") {
      break;
    }

    State begin = formula.begin();

    vector<int> ans = expression(begin);

    if (ans.empty()) {
      cout << "NULL" << endl;
    } else {
      cout << ans[0];

      for (int i = 1; i < ans.size(); i++) {
        cout << " " << ans[i];
      }

      cout << endl;
    }
  }

  return 0;
}