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

#include <algorithm>
#include <cstdio>
#include <vector>
using namespace std;

int dp[110][110][15][15][4];
char board[110][110];

const int INF = 1 << 28;
int dx[] = {1, 0, -1, 0};
int dy[] = {0, -1, 0, 1};

struct Elem {
  int x, y, a, b, dir;
};

int N, M, A;
int sx, sy, gx, gy;
int dfs(int x, int y, int a, int b, int dir) {
  int &val = dp[x][y][a][b][dir];

  if (~val)
    return val;
  if (x == gx && y == gy)
    return val = 0;

  int nx, ny, na, nb, nd;
  vector<int> dirs = {dir, 3 - dir, dir ^ 1};
  vector<int> use_a = {0, 1, 0};
  vector<int> use_b = {0, 0, 1};

  val = INF;
  for (int k = 0; k < 3; k++) {
    nd = dirs[k];
    nx = x + dx[nd];
    ny = y + dy[nd];
    na = a + use_a[k];
    nb = b + use_b[k];

    if (x == sx && y == sy && k != 0)
      continue;
    if (nx < 0 || nx >= N || ny < 0 || ny >= M)
      continue;
    if (board[nx][ny] == '#')
      continue;
    if (na > A || nb > A)
      continue;

    char orig = board[x][y];
    if (x != sx || y != sy)
      board[x][y] = '#';
    val = min(val, dfs(nx, ny, na, nb, nd) + (k != 0));
    board[x][y] = orig;
  }
  return val;
}

int main() {
  scanf("%d%d%d", &N, &M, &A);
  for (int i = 0; i < N; i++) {
    for (int j = 0; j < M; j++) {
      scanf(" %c", &board[i][j]);
      if (board[i][j] == 'S')
        sx = i, sy = j;
      if (board[i][j] == 'G')
        gx = i, gy = j;
    }
  }

  fill(dp[0][0][0][0], dp[110][0][0][0], -1);
  int ans = dfs(sx, sy, 0, 0, 0);
  if (ans == INF)
    printf("-1\\n");
  else
    printf("%d\\n", ans);
  return 0;
}


Error: TLE

Fixed submission:

#include <algorithm>
#include <cstdio>
#include <queue>
#include <vector>
using namespace std;

int dp[110][110][15][15][4];
char board[110][110];

const int INF = 1 << 28;
int dx[] = {1, 0, -1, 0};
int dy[] = {0, -1, 0, 1};

struct Elem {
  int x, y, a, b, dir;
};

int N, M, A;
int sx, sy, gx, gy;
int dfs(int x, int y, int a, int b, int dir) {
  int &val = dp[x][y][a][b][dir];

  if (val != INF)
    return val;
  if (x == gx && y == gy)
    return val = 0;

  int nx, ny, na, nb, nd;
  vector<int> dirs = {dir, 3 - dir, dir ^ 1};
  vector<int> use_a = {0, 1, 0};
  vector<int> use_b = {0, 0, 1};

  for (int k = 0; k < 3; k++) {
    nd = dirs[k];
    nx = x + dx[nd];
    ny = y + dy[nd];
    na = a + use_a[k];
    nb = b + use_b[k];

    if (x == sx && y == sy && k != 0)
      continue;
    if (nx < 0 || nx >= N || ny < 0 || ny >= M)
      continue;
    if (board[nx][ny] == '#')
      continue;
    if (na > A || nb > A)
      continue;

    char orig = board[x][y];
    if (x != sx || y != sy)
      board[x][y] = '#';
    val = min(val, dfs(nx, ny, na, nb, nd) + (k != 0));
    board[x][y] = orig;
  }
  return val;
}

int main() {
  scanf("%d%d%d", &N, &M, &A);
  for (int i = 0; i < N; i++) {
    for (int j = 0; j < M; j++) {
      scanf(" %c", &board[i][j]);
      if (board[i][j] == 'S')
        sx = i, sy = j;
      if (board[i][j] == 'G')
        gx = i, gy = j;
    }
  }

  fill(dp[0][0][0][0], dp[110][0][0][0], INF);
  int ans = dfs(sx, sy, 0, 0, 0);
  if (ans == INF)
    printf("-1\\n");
  else
    printf("%d\\n", ans);
  return 0;
}