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

#include <algorithm>
#include <bitset>
#include <cfloat>
#include <climits>
#include <cmath>
#include <cstdio>
#include <iomanip>
#include <iostream>
#include <list>
#include <map>
#include <numeric>
#include <queue>
#include <set>
#include <sstream>
#include <stack>
#include <string>
#include <vector>
using namespace std;

int dy[] = {0, 1, 0, -1};
int dx[] = {1, 0, -1, 0};

int main() {
  for (;;) {
    int w, h;
    cin >> w >> h;
    if (w == 0)
      return 0;

    vector<string> grid(h, string(w, '0'));
    int sy, sx;
    for (int y = 0; y < h; ++y) {
      for (int x = 0; x < w; ++x) {
        cin >> grid[y][x];
        if (grid[y][x] == 'P') {
          sy = y;
          sx = x;
          grid[y][x] = '.';
        }
      }
    }

    int n;
    cin >> n;
    int tmp = 0;
    vector<int> change(10, -1);
    vector<vector<int>> sale(8, vector<int>(100, 0));
    for (int i = 0; i < n; ++i) {
      int g, d, s, e;
      cin >> g >> d >> s >> e;
      if (change[g] == -1) {
        change[g] = tmp;
        g = tmp;
        ++tmp;
      }
      for (int j = s; j < e; ++j)
        sale[g][j] = d;
    }

    for (int y = 0; y < h; ++y) {
      for (int x = 0; x < w; ++x) {
        if (grid[y][x] != '.') {
          if (change[grid[y][x] - '0'] == -1)
            grid[y][x] = '#';
          else
            grid[y][x] = change[grid[y][x] - '0'] + '0';
        }
      }
    }

    vector<vector<vector<int>>> dp(
        h, vector<vector<int>>(w, vector<int>(1 << 8, -1)));
    dp[sy][sx][0] = 0;
    int ret = 0;
    for (int t = 0; t < 100; ++t) {
      vector<vector<vector<int>>> next(
          h, vector<vector<int>>(w, vector<int>(1 << 8, -1)));
      for (int y = 0; y < h; ++y) {
        for (int x = 0; x < w; ++x) {
          for (int i = 0; i < (1 << 8); ++i) {
            if (dp[y][x][i] == -1)
              continue;

            bitset<8> bs(i);
            int add = 0;
            for (int j = 0; j < 4; ++j) {
              int y2 = y + dy[j];
              int x2 = x + dx[j];
              if (y2 < 0 || y2 >= h || x2 < 0 || x2 >= w)
                continue;
              if (isdigit(grid[y2][x2]) && !bs[grid[y2][x2] - '0'] &&
                  sale[grid[y2][x2] - '0'][t] > 0) {
                bs[grid[y2][x2] - '0'] = true;
                add += sale[grid[y2][x2] - '0'][t];
              }
            }

            for (int j = 0; j < 4; ++j) {
              int y2 = y + dy[j];
              int x2 = x + dx[j];
              if (y2 < 0 || y2 >= h || x2 < 0 || x2 >= w)
                continue;
              if (grid[y2][x2] == '.') {
                next[y2][x2][bs.to_ulong()] =
                    max(next[y2][x2][bs.to_ulong()], dp[y][x][i] + add);
                ret = max(ret, next[y2][x2][bs.to_ulong()]);
              }
            }
          }
        }
      }
      dp.swap(next);
    }

    cout << ret << endl;
  }
}

Error: TLE

Fixed submission:

#include <algorithm>
#include <bitset>
#include <cfloat>
#include <climits>
#include <cmath>
#include <cstdio>
#include <iomanip>
#include <iostream>
#include <list>
#include <map>
#include <numeric>
#include <queue>
#include <set>
#include <sstream>
#include <stack>
#include <string>
#include <vector>
using namespace std;

int dy[] = {0, 1, 0, -1};
int dx[] = {1, 0, -1, 0};

int main() {
  for (;;) {
    int w, h;
    cin >> w >> h;
    if (w == 0)
      return 0;

    vector<string> grid(h, string(w, '0'));
    int sy, sx;
    for (int y = 0; y < h; ++y) {
      for (int x = 0; x < w; ++x) {
        cin >> grid[y][x];
        if (grid[y][x] == 'P') {
          sy = y;
          sx = x;
          grid[y][x] = '.';
        }
      }
    }

    int n;
    cin >> n;
    int m = 0;
    vector<int> change(10, -1);
    vector<vector<int>> sale(8, vector<int>(100, 0));
    for (int i = 0; i < n; ++i) {
      int g, d, s, e;
      cin >> g >> d >> s >> e;
      if (change[g] == -1) {
        change[g] = m;
        g = m;
        ++m;
      }
      for (int j = s; j < e; ++j)
        sale[g][j] = d;
    }

    for (int y = 0; y < h; ++y) {
      for (int x = 0; x < w; ++x) {
        if (grid[y][x] != '.') {
          if (change[grid[y][x] - '0'] == -1)
            grid[y][x] = '#';
          else
            grid[y][x] = change[grid[y][x] - '0'] + '0';
        }
      }
    }

    vector<vector<vector<int>>> dp(
        h, vector<vector<int>>(w, vector<int>(1 << 8, -1)));
    dp[sy][sx][0] = 0;
    int ret = 0;
    for (int t = 0; t < 100; ++t) {
      vector<vector<vector<int>>> next(
          h, vector<vector<int>>(w, vector<int>(1 << 8, -1)));
      for (int y = 0; y < h; ++y) {
        for (int x = 0; x < w; ++x) {
          for (int i = 0; i < (1 << 8); ++i) {
            if (dp[y][x][i] == -1)
              continue;

            for (int j = 0; j < (1 << 4); ++j) {
              bitset<8> bs(i);
              bitset<4> select(j);

              int add = 0;
              for (int k = 0; k < 4; ++k) {
                int y2 = y + dy[k];
                int x2 = x + dx[k];
                if (y2 < 0 || y2 >= h || x2 < 0 || x2 >= w)
                  continue;
                if (select[k] && '0' <= grid[y2][x2] && grid[y2][x2] <= '9' &&
                    !bs[grid[y2][x2] - '0']) {
                  bs[grid[y2][x2] - '0'] = true;
                  add += sale[grid[y2][x2] - '0'][t];
                }
              }

              for (int k = 0; k < 4; ++k) {
                int y2 = y + dy[k];
                int x2 = x + dx[k];
                if (y2 < 0 || y2 >= h || x2 < 0 || x2 >= w)
                  continue;
                if (grid[y2][x2] == '.') {
                  next[y2][x2][bs.to_ulong()] =
                      max(next[y2][x2][bs.to_ulong()], dp[y][x][i] + add);
                  ret = max(ret, next[y2][x2][bs.to_ulong()]);
                }
              }
            }
          }
        }
      }
      dp.swap(next);
    }

    cout << ret << endl;
  }
}