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

#include <algorithm>
#include <cstring>
#include <iostream>
using namespace std;
typedef long long ll;
int hp[100];
int mp[100];
string target[100];
int damage[100];
ll dp1[2][100010], dp2[2][100010];

int main() {
  int n, m;
  while (cin >> n, n) {
    for (int i = 0; i < n; i++)
      cin >> hp[i];

    cin >> m;
    for (int i = 0; i < m; i++) {
      string s;
      cin >> s >> mp[i] >> target[i] >> damage[i];
      // cout << s <<" " <<mp[i]<<" " << target[i]<<" " << damage[i] <<endl;
    }

    memset(dp1, 0, sizeof dp1);
    memset(dp2, 0, sizeof dp2);
    for (int i = 1; i <= 100000; i++) {
      dp1[0][i] = dp2[0][i] = 1 << 30;
    }
    for (int i = 1; i <= m; i++) {
      for (int j = 0; j <= 100000; j++) {
        if (damage[i - 1] == 0) {
          dp1[i % 2][j] = dp1[(i - 1) % 2][j];
          dp2[i % 2][j] = dp2[(i - 1) % 2][j];
        } else if (target[i - 1] == "All") {
          dp1[i % 2][j] =
              min(dp1[(i - 1) % 2][j],
                  dp1[i % 2][max(0, j - damage[i - 1])] + mp[i - 1]);
          dp2[i % 2][j] = dp2[(i - 1) % 2][j];
        } else {
          dp2[i % 2][j] =
              min(dp2[(i - 1) % 2][j],
                  dp2[i % 2][max(0, j - damage[i - 1])] + mp[i - 1]);
          dp1[i % 2][j] = dp1[(i - 1) % 2][j];
        }
      }
    }

    ll ans = 1LL << 50;
    for (int i = 0; i <= 100000; i++) {
      ll sum = dp1[m % 2][i];
      // cout << i << " " << dp1[n][i] << endl;
      for (int j = 0; j < n; j++) {
        if (hp[j] - i <= 0)
          continue;
        sum += dp2[m % 2][hp[j] - i];
      }
      // cout << i << " " << sum <<endl;
      ans = min(ans, sum);
    }

    cout << ans << endl;
  }
}

Error: MLE

Fixed submission:

#include <algorithm>
#include <cstring>
#include <iostream>
using namespace std;
int hp[100];
int mp[100];
string target[100];
int damage[100];
int dp1[110][100010], dp2[110][100010];

int main() {
  int n, m;
  while (cin >> n, n) {
    for (int i = 0; i < n; i++)
      cin >> hp[i];

    cin >> m;
    for (int i = 0; i < m; i++) {
      string s;
      cin >> s >> mp[i] >> target[i] >> damage[i];
      // cout << s <<" " <<mp[i]<<" " << target[i]<<" " << damage[i] <<endl;
    }

    memset(dp1, 0, sizeof dp1);
    memset(dp2, 0, sizeof dp2);
    for (int i = 1; i <= 100000; i++) {
      dp1[0][i] = dp2[0][i] = 1 << 25;
    }
    for (int i = 1; i <= n; i++) {
      for (int j = 0; j <= 100000; j++) {
        if (target[i - 1] == "All") {
          dp1[i][j] =
              min(dp1[i - 1][j], dp1[i][max(0, j - damage[i - 1])] + mp[i - 1]);
          dp2[i][j] = dp2[i - 1][j];
        } else {
          dp2[i][j] =
              min(dp2[i - 1][j], dp2[i][max(0, j - damage[i - 1])] + mp[i - 1]);
          dp1[i][j] = dp1[i - 1][j];
        }
      }
    }

    for (int i = 5000; i <= 10000; i++) {
      // cout << i << " " << dp2[n][i] <<endl;
    }

    int ans = 1 << 25;
    for (int i = 0; i <= 100000; i++) {
      int sum = dp1[n][i];
      // cout << i << " " << dp1[n][i];
      for (int j = 0; j < n; j++) {
        if (hp[j] - i <= 0)
          continue;
        sum += dp2[n][hp[j] - i];
      }
      // cout << i << " " << sum <<endl;
      ans = min(ans, sum);
    }

    cout << ans << endl;
  }
}