Problem p00109 (C++) — buggy submission, verdict: Runtime Error

#include <iostream>
#include <string>
using namespace std;

class calc {
  string s;
  string::iterator it;

public:
  calc(string str) {
    s = str;
    it = str.begin();
  }

  int fact() {
    if (*it == '(') {
      *it++;
      int ret = exp();
      *it++;
      return ret;
    } else {
      int ret = 0;
      while ('0' <= *it && *it <= '9') {
        ret *= 10;
        ret += *it - '0';
        ++it;
      }
      return ret;
    }
  }

  int turm() {
    int ret = fact();
    while (*it == '*' || *it == '/') {
      if (*it == '*') {
        *it++;
        ret *= fact();

      } else if (*it == '/') {
        *it++;
        ret /= fact();
      }
    }
    return ret;
  }
  int exp() {
    int ret = turm();
    while (*it == '+' || *it == '-') {
      if (*it == '+') {
        *it++;
        ret += turm();

      } else if (*it == '-') {
        *it++;
        ret -= turm();
      }
    }
    return ret;
  }
};

int main() {
  int n;
  cin >> n;
  while (n--) {
    string str;
    cin >> str;
    calc ans(str);
    cout << ans.exp() << endl;
  }
  return 0;
}

Error: 0

Fixed submission:

#include <algorithm>
#include <iostream>
#include <sstream>
using namespace std;
int n;
string str;
int start, goal;
void kake();
void tasi();
void tume(int, int);
int Getnum1(int);
int Getnum2(int);
string i2s(int);

string i2s(int num) {
  stringstream ss;
  string str;
  ss << num;
  ss >> str;
  return str;
}

int Getnum1(int i) {

  string num = "";
  while (1) {
    if (!('0' <= str[i] && str[i] <= '9') || 0 > i)
      break;
    num += str[i];
    str[i] = '#';
    i--;
  }
  //  cout << str << endl;
  //  cout << "num "<<num << endl;
  reverse(num.begin(), num.end());
  return atoi(num.c_str());
}

int Getnum2(int i) {

  string num = "";
  while (1) {
    if (!('0' <= str[i] && str[i] <= '9') || str.size() < i)
      break;
    num += str[i];
    str[i] = '#';
    i++;
  }
  return atoi(num.c_str());
}

void tume(int s, int g) {
  string str2 = "";
  for (int i = 0; i < str.size(); i++) {
    if (str[i] != '#' && (s != i || g != i))
      str2 += str[i];
  }
  str = str2;
}

void cal() {
  kake();
  tasi();
}

void kake() {
  for (int i = start; i <= goal; i++) {
    //    cout << start << ' ' << goal<<endl;
    if (str[i] == '*') {
      int t1 = Getnum1(i - 1);
      int t2 = Getnum2(i + 1);
      int t = t1 * t2;
      int len1 = i2s(t1).size();
      int len2 = i2s(t2).size();
      int len3 = i2s(t).size();
      str.replace(i - len1, i + len2 - start, i2s(t));
      tume(i - 1, i + 1);
      //
      //      cout << str << endl;
      i = start;
      goal = goal - ((len1 + len2 + 1) - len3);
      //      cout << "goal "<<goal << endl;
    }
    if (str[i] == '/') {
      int t1 = Getnum1(i - 1);
      int t2 = Getnum2(i + 1);
      int t = t1 / t2;
      int len1 = i2s(t1).size();
      int len2 = i2s(t2).size();
      int len3 = i2s(t).size();
      str.replace(i - len1, i + len2 - start, i2s(t));
      tume(i - 1, i + 1);
      //
      i = start;
      goal = goal - ((len1 + len2 + 1) - len3);
      //      cout << "goal "<<goal << endl;
    }
  }
}
void tasi() {
  for (int i = start; i <= goal; i++) {
    if (str[i] == '+') {
      int t1 = Getnum1(i - 1);
      int t2 = Getnum2(i + 1);
      int t = t1 + t2;
      int len1 = i2s(t1).size();
      int len2 = i2s(t2).size();
      int len3 = i2s(t).size();
      str.replace(i - len1, i + len2 - start, i2s(t));
      tume(i - 1, i + 1);
      //
      i = start;
      goal = goal - ((len1 + len2 + 1) - len3);
      //      cout << "goal "<<goal << endl;
    }
    if (str[i] == '-') {
      int t1 = Getnum1(i - 1);
      int t2 = Getnum2(i + 1);
      int t = t1 - t2;
      int len1 = i2s(t1).size();
      int len2 = i2s(t2).size();
      int len3 = i2s(t).size();
      str.replace(i - len1, i + len2 - start, i2s(t));
      tume(i - 1, i + 1);
      //      cout << '-' << endl;      cout << str << endl;
      i = start;
      goal = goal - ((len1 + len2 + 1) - len3);
    }
  }
}

int main() {
  cin >> n;
  while (n--) {
    str = "";
    cin >> str;

    if (str[0] == '#')
      break;

    for (int i = 0; i < str.size(); i++) {
      if (str[i] == '(')
        start = i;
      if (str[i] == ')') {
        goal = i;
        cal();
        str[start] = '#';
        str[goal] = '#';
        tume(start, goal);
        i = -1;
        continue;
      }
    }
    start = 0, goal = str.size() - 1;
    cal();
    int ans = atoi(str.c_str());
    cout << ans << endl;
  }
  return 0;
}