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

#include <algorithm>
#include <cmath>
#include <complex>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <deque>
#include <functional>
#include <iostream>
#include <list>
#include <map>
#include <numeric>
#include <queue>
#include <set>
#include <string>
#include <utility>
#include <vector>

using namespace std;

/* constant */

const int MAX_N = 100;
const int MAX_P = 10;
const int MAX_LEN = 200;

const int MAX_E = MAX_P * MAX_LEN;

const int INF = 1 << 30;

/* typedef */

/* global variables */

int n, ulen, pis[MAX_N], wlens[MAX_N];
string wis[MAX_N], usp;
bool mtx[MAX_N][MAX_LEN];
int dp0[MAX_LEN + 1], dp1[MAX_E + 1];

/* subroutines */

bool strmatch(string &s0, string &sub, int i) {
  for (int j = 0; j < sub.size(); j++)
    if (s0[i + j] != sub[j])
      return false;
  return true;
}

/* main */

int main() {
  for (int cn = 1;; cn++) {
    cin >> n;
    if (n == 0)
      break;

    for (int i = 0; i < n; i++) {
      cin >> wis[i] >> pis[i];
      wlens[i] = wis[i].size();
    }

    cin >> usp;
    ulen = usp.size();

    for (int i = 0; i < n; i++)
      for (int j = 0; j < ulen; j++)
        mtx[i][j] = strmatch(usp, wis[i], j);

    for (int i = 1; i <= ulen; i++)
      dp0[i] = -1;
    dp0[0] = 0;

    for (int k = 0; k <= ulen; k++)
      if (dp0[k] >= 0)
        for (int i = 0; i < n; i++)
          if (mtx[i][k]) {
            int ki = k + wlens[i];
            if (ki <= ulen)
              dp0[ki] = max(dp0[ki], dp0[k] + pis[i]);
          }

    int max_exp = dp0[ulen];
    // cout << max_exp << endl;

    for (int i = 1; i <= max_exp; i++)
      dp1[i] = INF;
    dp1[0] = 0;

    for (int e = 0; e <= max_exp; e++)
      if (dp1[e] < INF)
        for (int i = 0; i < n; i++) {
          int ei = e + pis[i];
          if (ei <= max_exp)
            dp1[ei] = min(dp1[ei], dp1[e] + wlens[i]);
        }

    printf("Case %d: %d\\n", cn, dp1[max_exp]);
  }

  return 0;
}

Error: TLE

Fixed submission:

#include <algorithm>
#include <cmath>
#include <complex>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <deque>
#include <functional>
#include <iostream>
#include <list>
#include <map>
#include <numeric>
#include <queue>
#include <set>
#include <string>
#include <utility>
#include <vector>

using namespace std;

/* constant */

const int MAX_N = 100;
const int MAX_P = 10;
const int MAX_LEN = 200;

const int MAX_E = MAX_P * MAX_LEN;

const int INF = 1 << 30;

/* typedef */

/* global variables */

int n, ulen, pis[MAX_N], wlens[MAX_N];
string wis[MAX_N], usp;
bool mtx[MAX_N][MAX_LEN];
int dp[MAX_E + 1];

/* subroutines */

bool strmatch(string &s0, string &sub, int i) {
  for (int j = 0; j < sub.size(); j++)
    if (s0[i + j] != sub[j])
      return false;
  return true;
}

int rec_max(int k) {
  if (k > ulen)
    return -1;
  if (k == ulen)
    return 0;

  int max_e = 0;

  for (int i = 0; i < n; i++) {
    if (mtx[i][k]) {
      int rmk = rec_max(k + wlens[i]);
      if (rmk < 0)
        continue;
      int e = pis[i] + rmk;
      if (max_e < e)
        max_e = e;
    }
  }

  return max_e;
}

/* main */

int main() {
  for (int cn = 1;; cn++) {
    cin >> n;
    if (n == 0)
      break;

    for (int i = 0; i < n; i++) {
      cin >> wis[i] >> pis[i];
      wlens[i] = wis[i].size();
    }

    cin >> usp;
    ulen = usp.size();

    for (int i = 0; i < n; i++)
      for (int j = 0; j < ulen; j++)
        mtx[i][j] = strmatch(usp, wis[i], j);

    int max_exp = rec_max(0);
    // cout << max_exp << endl;

    for (int i = 1; i <= max_exp; i++)
      dp[i] = INF;
    dp[0] = 0;

    for (int e = 0; e <= max_exp; e++)
      if (dp[e] < INF)
        for (int i = 0; i < n; i++) {
          int ei = e + pis[i];
          if (ei <= max_exp)
            dp[ei] = min(dp[ei], dp[e] + wlens[i]);
        }

    printf("Case %d: %d\\n", cn, dp[max_exp]);
  }

  return 0;
}