Problem p02863 (C++)

Buggy submission (status: Time Limit Exceeded):
#include <bits/stdc++.h>
using namespace std;
template <typename T> void read(T &t) {
  t = 0;
  char ch = getchar();
  int f = 1;
  while (ch < '0' || ch > '9') {
    if (ch == '-')
      f = -1;
    ch = getchar();
  }
  do {
    (t *= 10) += ch - '0';
    ch = getchar();
  } while ('0' <= ch && ch <= '9');
  t *= f;
}
const int maxn = 3010;
int n, T, a[maxn], b[maxn];
int dp[maxn][maxn], ans;
int dp2[maxn][maxn], mx[maxn][maxn];
void update(int &x, int y) { x = max(x, y); }
int main() {
  // freopen("1.txt","r",stdin);
  read(n);
  read(T);
  T--;
  for (int i = 1; i <= n; i++)
    read(a[i]), read(b[i]);
  for (int i = 1; i <= n; i++) {
    for (int j = 0; j <= T; j++)
      update(dp[i][j], dp[i - 1][j]);
    for (int j = 0; j + a[i] <= T; j++)
      update(dp[i][j + a[i]], dp[i - 1][j] + b[i]);
  }
  for (int i = n; i >= 1; i--) {
    for (int j = 0; j <= T; j++)
      update(dp2[i][j], dp2[i + 1][j]);
    for (int j = 0; j + a[i] <= T; j++)
      update(dp2[i][j + a[i]], dp2[i + 1][j] + b[i]);
  }
  for (int i = 1; i <= n; i++) {
    mx[i][0] = dp2[i][0];
    for (int j = 1; j <= T; j++)
      mx[i][j] = max(mx[i][j - 1], dp2[i][j]);
  }
  for (int i = 1; i <= n; i++) {
    for (int j = 0; j <= T; j++)
      for (int k = 0; k + j <= T; k++) {
        update(ans, dp[i - 1][j] + dp2[i + 1][k] + b[i]);
      }
  }
  printf("%d\n", ans);
  return 0;
}
/*
  REMEMBER:
  1. Think TWICE, Code ONCE!
  Are there any counterexamples to your algo?

  2. Be careful about the BOUNDARIES!
  N=1? P=1? Something about 0?

  3. Do not make STUPID MISTAKES!
  Array size? Integer overflow? Time complexity? Memory usage? Precision error?
*/

Fixed submission:
#include <bits/stdc++.h>
using namespace std;
template <typename T> void read(T &t) {
  t = 0;
  char ch = getchar();
  int f = 1;
  while (ch < '0' || ch > '9') {
    if (ch == '-')
      f = -1;
    ch = getchar();
  }
  do {
    (t *= 10) += ch - '0';
    ch = getchar();
  } while ('0' <= ch && ch <= '9');
  t *= f;
}
const int maxn = 3010;
int n, T, a[maxn], b[maxn];
int dp[maxn][maxn], ans;
int dp2[maxn][maxn], mx[maxn][maxn];
void update(int &x, int y) { x = max(x, y); }
int main() {
  // freopen("1.txt","r",stdin);
  read(n);
  read(T);
  T--;
  for (int i = 1; i <= n; i++)
    read(a[i]), read(b[i]);
  for (int i = 1; i <= n; i++) {
    for (int j = 0; j <= T; j++)
      update(dp[i][j], dp[i - 1][j]);
    for (int j = 0; j + a[i] <= T; j++)
      update(dp[i][j + a[i]], dp[i - 1][j] + b[i]);
  }
  for (int i = n; i >= 1; i--) {
    for (int j = 0; j <= T; j++)
      update(dp2[i][j], dp2[i + 1][j]);
    for (int j = 0; j + a[i] <= T; j++)
      update(dp2[i][j + a[i]], dp2[i + 1][j] + b[i]);
  }
  for (int i = 1; i <= n; i++) {
    mx[i][0] = dp2[i][0];
    for (int j = 1; j <= T; j++)
      mx[i][j] = max(mx[i][j - 1], dp2[i][j]);
  }
  for (int i = 1; i <= n; i++) {
    for (int j = 0; j <= T; j++)
      update(ans, dp[i - 1][j] + mx[i + 1][T - j] + b[i]);
  }
  printf("%d\n", ans);
  return 0;
}
/*
  REMEMBER:
  1. Think TWICE, Code ONCE!
  Are there any counterexamples to your algo?

  2. Be careful about the BOUNDARIES!
  N=1? P=1? Something about 0?

  3. Do not make STUPID MISTAKES!
  Array size? Integer overflow? Time complexity? Memory usage? Precision error?
*/