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

#include <iostream>
#include <queue>
#include <vector>
#define INF 1e+9
#define mp make_pair
using namespace std;

struct edge {
  int to, cost;
};
typedef pair<int, int> POS;  // x,y
typedef pair<int, POS> FOOT; // foot
typedef pair<int, FOOT> P;   // cost

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

int main() {
  int w, h;
  while (cin >> w >> h, w) {
    int field[60][30], d[60][30][2];
    priority_queue<P, vector<P>, greater<P>> que;
    vector<POS> t;
    for (int i = 0; i < 60; i++) {
      for (int j = 0; j < 30; j++) {
        d[i][j][0] = INF;
        d[i][j][1] = INF;
      }
    }
    for (int i = 0; i < h; i++) {
      for (int j = 0; j < w; j++) {
        char c;
        cin >> c;
        if (c != 'X') {
          if (c == 'S') {
            d[i][j][0] = 0;
            d[i][j][1] = 0;
            field[i][j] = 0;
            que.push(mp(0, mp(-1, mp(i, j))));
            que.push(mp(0, mp(1, mp(i, j))));
          } else if (c == 'T') {
            t.push_back(mp(i, j));
            field[i][j] = 0;
          } else
            field[i][j] = c - '0';
        } else
          field[i][j] = INF;
      }
    }
    while (!que.empty()) {
      P p = que.top();
      que.pop();
      int cost = p.first, foot = p.second.first, x = p.second.second.first,
          y = p.second.second.second;
      int fa = (foot + 1) / 2, _fa = (1 - foot) / 2;
      if (d[x][y][fa] < cost)
        continue;
      for (int i = 0; i < 9; i++) {
        int nx = x + foot * dx[i], ny = y + foot * dy[i];
        if (nx >= 0 && nx < h && ny >= 0 && ny < w && field[nx][ny] != INF &&
            d[nx][ny][_fa] > d[x][y][fa] + field[nx][ny]) {
          d[nx][ny][_fa] = d[x][y][fa] + field[nx][ny];
          que.push(mp(d[nx][ny][_fa], mp(-foot, mp(nx, ny))));
        }
      }
    }
    int mi = INF;
    for (int i = 0; i < t.size(); i++) {
      for (int j = 0; j < 2; j++) {
        mi = min(mi, d[t[i].first][t[i].second][j]);
      }
    }
    if (mi != INF)
      cout << mi << endl;
    else
      cout << -1 << endl;
  }
  return 0;
}

Error: TLE

Fixed submission:

#include <iostream>
#include <queue>
#include <vector>
#define INF 1e+9
using namespace std;

int dx[] = {-2, -1, -1, 0, 0, 0, 1, 1, 2}, dy[] = {1, 1, 2, 1, 2, 3, 1, 2, 1};
struct edge {
  int to, cost;
};
typedef pair<int, int> P;

int w, h;
int field[60][30], d[60][30][2];
vector<P> s;

void dfs(int x, int y, int t, int foot) {
  if (field[x][y] == -1) {
    d[x][y][(foot + 1) / 2] = t;
    return;
  }
  if (t > d[x][y][(foot + 1) / 2])
    return;
  d[x][y][(foot + 1) / 2] = t;
  for (int i = 0; i < 9; i++) {
    int nx = x + dx[i], ny = y + foot * dy[i];
    if (nx >= 0 && nx < h && ny >= 0 && ny < w && field[nx][ny] != INF &&
        t + field[x][y] < d[nx][ny][(1 - foot) / 2]) {
      dfs(nx, ny, t + field[x][y], -foot);
    }
  }
}

int main() {
  while (1) {
    cin >> w >> h;
    if (!w)
      break;
    s.clear();
    for (int i = 0; i < 60; i++) {
      for (int j = 0; j < 30; j++) {
        d[i][j][0] = INF;
        d[i][j][1] = INF;
      }
    }
    for (int i = 0; i < h; i++) {
      for (int j = 0; j < w; j++) {
        char c;
        cin >> c;
        if (c != 'X') {
          if (c == 'S') {
            s.push_back(P(i, j));
            d[i][j][0] = 0;
            d[i][j][1] = 0;
            field[i][j] = 0;
          } else if (c == 'T') {
            field[i][j] = -1;
          } else
            field[i][j] = c - '0';
        } else
          field[i][j] = INF;
      }
    }
    int mi = INF;
    for (int i = 0; i < (int)s.size(); i++) {
      for (int j = -1; j <= 1; j += 2) {
        dfs(s[i].first, s[i].second, 0, j);
        for (int k = 0; k < h; k++) {
          for (int l = 0; l < w; l++) {
            if (field[k][l] == -1)
              mi = min(mi, min(d[k][l][0], d[k][l][1]));
            if (field[k][l] != 0) {
              d[k][l][0] = INF;
              d[k][l][1] = INF;
            }
          }
        }
      }
    }
    if (mi != INF)
      cout << mi << endl;
    else
      cout << -1 << endl;
  }
  return 0;
}