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

#include <algorithm>
#include <cassert>
#include <cstdio>
#include <cstring>
#include <iostream>
#include <map>
#include <queue>
using namespace std;
typedef pair<int, int> P;
class state {
public:
  char f[11][11], c, l;
  state() {}
  state(int c, int l) : c(c), l(l){};
};
char in[11][11];
state ne;
bool used[11][11];
const int dx[4] = {0, 0, 1, -1};
const int dy[4] = {1, -1, 0, 0};
int n, m;
int res;

void dfs(int next, int prev, int x, int y) {
  if (x == 0 && y == 0) {
    memset(used, false, sizeof(used));
  }
  ne.f[x][y] = next;
  used[x][y] = true;
  for (int i = 0; i < 4; i++) {
    int nx = x + dx[i], ny = y + dy[i];
    if (nx >= 0 && nx < n && ny >= 0 && ny < m) {
      if (!used[nx][ny]) {
        used[nx][ny] = true;
        if (ne.f[nx][ny] == next) {
        }
        if (ne.f[nx][ny] == prev) {
          dfs(next, prev, nx, ny);
        }
      }
    }
  }
}

void cnt(int prev, int x, int y) {
  if (x == 0 && y == 0) {
    ne.l = 0;
    memset(used, false, sizeof(used));
  }
  ne.l++;
  used[x][y] = true;
  for (int i = 0; i < 4; i++) {
    int nx = x + dx[i], ny = y + dy[i];
    if (nx >= 0 && nx < n && ny >= 0 && ny < m) {
      if (!used[nx][ny]) {
        used[nx][ny] = true;
        if (ne.f[nx][ny] == prev) {
          cnt(prev, nx, ny);
        }
      }
    }
  }
}

void bfs(state init) {
  queue<state> que;
  // map<state, bool> v;
  res = 50;
  // v[ne]= true;
  que.push(init);
  while (que.size()) {
    state p = que.front();
    que.pop();
    if (p.c >= res)
      break;
    ne.c = p.c + 1;
    for (int i = 0; i <= 2; i++) {
      memcpy(ne.f, p.f, sizeof(ne.f));
      dfs(i, ne.f[0][0], 0, 0);
      cnt(ne.f[0][0], 0, 0);
      // if(!V[ne.f]){
      if (ne.l == n * m)
        res = min(res, p.c + 1);
      else if (ne.l > p.l)
        que.push(ne);
      //	V[ne.f]=true;
      //}
    }
  }
}

int main(void) {
  while (1) {
    res = 100;
    scanf("%d%d\\n", &n, &m);
    if (n == 0 && m == 0)
      break;
    state init = state(0, 1);
    for (int i = 0; i < m; i++) {
      for (int j = 0; j < n; j++) {
        cin >> in[j][i];
        if (in[j][i] == 'R')
          init.f[j][i] = 0;
        if (in[j][i] == 'G')
          init.f[j][i] = 1;
        if (in[j][i] == 'B')
          init.f[j][i] = 2;
      }
    }
    memcpy(ne.f, init.f, sizeof(ne.f));
    cnt(ne.f[0][0], 0, 0);
    if (ne.l == n * m)
      printf("0\\n");
    else {
      bfs(init);
      printf("%d\\n", res);
    }
  }
  return 0;
}

Error: TLE

Fixed submission:

#include <algorithm>
#include <cstdio>
#include <cstring>
#include <iostream>
#include <map>
#include <queue>
using namespace std;
typedef pair<int, int> P;
struct state {
  char f[11][11];
  int c, l;
  state() {}
  state(int c, int l) : c(c), l(l){};
};
char in[11][11];
state ne;
bool used[11][11];
const int dx[4] = {0, 0, 1, -1};
const int dy[4] = {1, -1, 0, 0};
int n, m;
int res;

void dfs(int next, int prev, int x, int y) {
  if (x == 0 && y == 0) {
    memset(used, false, sizeof(used));
  }
  ne.f[x][y] = next;
  used[x][y] = true;
  for (int i = 0; i < 4; i++) {
    int nx = x + dx[i], ny = y + dy[i];
    if (nx >= 0 && nx < n && ny >= 0 && ny < m) {
      if (!used[nx][ny]) {
        used[nx][ny] = true;
        if (ne.f[nx][ny] == next) {
        }
        if (ne.f[nx][ny] == prev) {
          dfs(next, prev, nx, ny);
        }
      }
    }
  }
}

void cnt(int prev, int x, int y) {
  if (x == 0 && y == 0) {
    ne.l = 0;
    memset(used, false, sizeof(used));
  }
  ne.l++;
  used[x][y] = true;
  for (int i = 0; i < 4; i++) {
    int nx = x + dx[i], ny = y + dy[i];
    if (nx >= 0 && nx < n && ny >= 0 && ny < m) {
      if (!used[nx][ny]) {
        used[nx][ny] = true;
        if (ne.f[nx][ny] == prev) {
          cnt(prev, nx, ny);
        }
      }
    }
  }
}

void bfs(state init) {
  queue<state> que;
  // map<state, bool> V;
  res = 50;
  // V[init]=true;
  que.push(init);
  while (que.size()) {
    state p = que.front();
    que.pop();
    ne.c = p.c + 1;
    for (int i = 0; i <= 2; i++) {
      memcpy(ne.f, p.f, sizeof(ne.f));
      dfs(i, ne.f[0][0], 0, 0);
      cnt(ne.f[0][0], 0, 0);
      // if(!V[ne]){
      if (ne.l == n * m)
        res = min(res, p.c + 1);
      else if (ne.l > p.l)
        que.push(ne);
      //	V[ne]=true;
      //}
    }
  }
}

int main(void) {
  while (1) {
    res = 100;
    scanf("%d%d\\n", &n, &m);
    if (n == 0 && m == 0)
      break;
    state init = state(0, 1);
    for (int i = 0; i < m; i++) {
      for (int j = 0; j < n; j++) {
        cin >> in[j][i];
        if (in[j][i] == 'R')
          init.f[j][i] = 0;
        if (in[j][i] == 'G')
          init.f[j][i] = 1;
        if (in[j][i] == 'B')
          init.f[j][i] = 2;
      }
    }
    memcpy(ne.f, init.f, sizeof(ne.f));
    cnt(ne.f[0][0], 0, 0);
    if (ne.l == n * m)
      printf("0\\n");
    else {
      bfs(init);
      printf("%d\\n", res);
    }
  }
  return 0;
}