Problem p00215 (C++) — buggy submission, verdict: Memory Limit Exceeded

#include <bits/stdc++.h>
using namespace std;

#define for_(i, a, b) for (int i = (a); i < (b); ++i)

struct Node {
  int x, y;
};

int H, W, sx, sy, gx, gy;
string grid[1000];
vector<Node> nodes[5];
vector<int> dst[5];

int solve(int init_c) {
  for_(i, 0, 5) dst[i].assign(nodes[i].size(), (int)1e9);

  int sc = (init_c + 1) % 5;

  for_(i, 0, (int)nodes[sc].size()) {
    dst[sc][i] = abs(sx - nodes[sc][i].x) + abs(sy - nodes[sc][i].y);
  }

  for_(i, 1, 4) {
    int c = (init_c + i) % 5;
    int nc = (c + 1) % 5;

    int A = nodes[c].size(), B = nodes[nc].size();

    for_(j, 0, A) {
      int x1 = nodes[c][j].x;
      int y1 = nodes[c][j].y;

      for_(k, 0, B) {
        int x2 = nodes[nc][k].x;
        int y2 = nodes[nc][k].y;

        dst[nc][k] = min(dst[nc][k], dst[c][j] + abs(x1 - x2) + abs(y1 - y2));
      }
    }
  }

  int gc = (init_c + 4) % 5;
  int res = (int)1e9, M = nodes[gc].size();

  for_(i, 0, M) res = min(res, dst[gc][i] + abs(gx - nodes[gc][i].x) +
                                   abs(gy - nodes[gc][i].y));

  return res;
}

int main() {
  while (cin >> W >> H, W) {
    for_(i, 0, 5) nodes[i].clear();

    for_(i, 0, H) {
      cin >> grid[i];

      for_(j, 0, W) {
        if (grid[i][j] == 'S') {
          sx = j;
          sy = i;
        } else if (grid[i][j] == 'G') {
          gx = j;
          gy = i;
        } else if (grid[i][j] != '.')
          nodes[grid[i][j] - '1'].push_back(Node{j, i});
      }
    }

    int ansc = 0, mini = (int)1e9;

    for_(i, 0, 5) {
      int res = solve(i);

      if (mini > res) {
        mini = res;
        ansc = i;
      }
    }

    if (mini < (int)1e9)
      cout << ansc + 1 << " " << mini << endl;
    else
      cout << "NA" << endl;
  }
}

Error: MLE

Fixed submission:

#include <bits/stdc++.h>
using namespace std;

#define for_(i, a, b) for (int i = (a); i < (b); ++i)

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

bool in_range(int x, int mn, int mx) { return mn <= x && x < mx; }
bool in_range(int x, int y, int w, int h) {
  return in_range(x, 0, w) && in_range(y, 0, h);
}

struct State {
  int x, y, c;
};

int H, W, dst[1000][1000][32], sx, sy, gx, gy;
string grid[1000];

int solve(int init_c) {
  memset(dst, -1, sizeof(dst));

  queue<State> que;
  que.push(State{sx, sy, 1 << init_c});

  dst[sy][sx][1 << init_c] = 0;

  while (!que.empty()) {
    State s = que.front();
    que.pop();

    if (s.c == (1 << 5) - 1 && s.x == gx && s.y == gy) {
      return dst[s.y][s.x][s.c];
    }

    int step = dst[s.y][s.x][s.c];

    for_(d, 0, 4) {
      int nx = s.x + dx[d], ny = s.y + dy[d];

      if (!in_range(nx, ny, W, H))
        continue;

      int nc = s.c;

      if (isdigit(grid[ny][nx])) {
        int c = (grid[ny][nx] - '1');
        int b = (c + 4) % 5;

        if (s.c >> b & 1)
          nc |= 1 << c;
      }

      if (dst[ny][nx][nc] == -1) {
        dst[ny][nx][nc] = step + 1;
        que.push(State{nx, ny, nc});
      }
    }
  }

  return (int)1e9;
}

int main() {
  while (cin >> W >> H, W) {
    for_(i, 0, H) {
      cin >> grid[i];
      for_(j, 0, W) {
        if (grid[i][j] == 'S') {
          sx = j;
          sy = i;
        }
        if (grid[i][j] == 'G') {
          gx = j;
          gy = i;
        }
      }
    }

    int ansc = 0, mini = (int)1e9;

    for_(i, 0, 5) {
      int res = solve(i);

      if (mini > res) {
        mini = res;
        ansc = i;
      }
    }

    if (mini < (int)1e9)
      cout << ansc + 1 << " " << mini << endl;
    else
      cout << "NA" << endl;
  }
}