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

#include <algorithm>
#include <cmath>
#include <complex>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <functional>
#include <iostream>
#include <list>
#include <map>
#include <numeric>
#include <queue>
#include <set>
#include <sstream>
#include <stack>
#include <string>
#include <vector>

#define mp make_pair
#define pb push_back
#define all(x) (x).begin(), (x).end()
#define rep(i, n) for (int i = 0; i < (n); i++)

using namespace std;

typedef long long ll;
typedef unsigned long long ull;
typedef vector<bool> vb;
typedef vector<int> vi;
typedef vector<vb> vvb;
typedef vector<vi> vvi;
typedef pair<int, int> pii;

const int INF = 1 << 29;
const double EPS = 1e-9;

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

const int boardw = 3;

struct BOARD {
  int map[boardw][boardw];
};

bool check(BOARD &b) {
  for (int i = 0; i < boardw; ++i) {
    for (int j = 0; j < boardw; ++j) {
      if (b.map[i][j] == 0)
        continue;
      int tgt = i * boardw + j + 1;
      if (b.map[i][j] != tgt) {
        return false;
      }
    }
  }
  return true;
}

int dfs(BOARD &b, int depth, int dir) {
  if (depth == 0) {
    if (check(b)) {
      return 1;
    } else {
      return -1;
    }
  }

  int px, py;
  for (int i = 0; i < boardw; ++i) {
    for (int j = 0; j < boardw; ++j) {
      if (b.map[i][j] == 0) {
        px = j;
        py = i;
      }
    }
  }
  int est = 0;
  for (int i = 0; i < boardw; ++i) {
    for (int j = 0; j < boardw; ++j) {
      if (i * j == boardw * boardw)
        continue;
      for (int k = 0; k < boardw; ++k) {
        for (int l = 0; l < boardw; ++l) {
          if (i * boardw + j + 1 == b.map[k][l]) {
            est += std::abs(k - i) + std::abs(l - j);
          }
        }
      }
    }
  }
  if (est > depth) {
    return -1;
  }
  int dx[] = {0, 1, 0, -1};
  int dy[] = {1, 0, -1, 0};
  for (int k = 0; k < 4; k++) {
    if (dir != -1 && k == (dir + 2) % 4) {
      continue;
    }
    int tx = px + dx[k];
    int ty = py + dy[k];
    if (tx < 0 || tx >= boardw || ty < 0 || ty >= boardw)
      continue;
    int temp = b.map[py][px];
    b.map[py][px] = b.map[ty][tx];
    b.map[ty][tx] = temp;

    int ret = dfs(b, depth - 1, k);

    temp = b.map[py][px];
    b.map[py][px] = b.map[ty][tx];
    b.map[ty][tx] = temp;
    if (ret != -1)
      return ret;
  }
  return -1;
}

int main(int argc, char const *argv[]) {
  BOARD b;
  for (int i = 0; i < boardw; ++i) {
    for (int j = 0; j < boardw; ++j) {
      cin >> b.map[i][j];
    }
  }
  if (check(b)) {
    cout << 0 << endl;
    return 0;
  }
  int i = 0;
  while (++i) {
    int ret = dfs(b, i, -1);
    if (ret == 1) {
      cout << i << endl;
      return 0;
    }
  }

  return 0;
}

Error: TLE

Fixed submission:

#include <algorithm>
#include <cmath>
#include <complex>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <functional>
#include <iostream>
#include <list>
#include <map>
#include <numeric>
#include <queue>
#include <set>
#include <sstream>
#include <stack>
#include <string>
#include <vector>

#define mp make_pair
#define pb push_back
#define all(x) (x).begin(), (x).end()
#define rep(i, n) for (int i = 0; i < (n); i++)

using namespace std;

typedef long long ll;
typedef unsigned long long ull;
typedef vector<bool> vb;
typedef vector<int> vi;
typedef vector<vb> vvb;
typedef vector<vi> vvi;
typedef pair<int, int> pii;

const int INF = 1 << 29;
const double EPS = 1e-9;

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

const int boardw = 3;

struct BOARD {
  int map[boardw][boardw];
};

std::queue<BOARD> q;
std::map<BOARD, int> m;

bool check(BOARD b) {
  for (int i = 0; i < boardw; ++i) {
    for (int j = 0; j < boardw; ++j) {
      if (b.map[i][j] == 0)
        continue;
      int tgt = i * boardw + j + 1;
      if (b.map[i][j] != tgt) {
        return false;
      }
    }
  }
  return true;
}

int dfs(BOARD &b, int depth, int dir) {
  if (depth == 0) {
    if (check(b)) {
      return 1;
    } else {
      return -1;
    }
  }

  int px, py;
  for (int i = 0; i < boardw; ++i) {
    for (int j = 0; j < boardw; ++j) {
      if (b.map[i][j] == 0) {
        px = j;
        py = i;
      }
    }
  }
  int dx[] = {0, 1, 0, -1};
  int dy[] = {1, 0, -1, 0};
  for (int k = 0; k < 4; k++) {
    if (dir != -1 && k == (dir + 2) % 4) {
      continue;
    }
    int tx = px + dx[k];
    int ty = py + dy[k];
    if (tx < 0 || tx >= boardw || ty < 0 || ty >= boardw)
      continue;
    int temp = b.map[py][px];
    b.map[py][px] = b.map[ty][tx];
    b.map[ty][tx] = temp;

    int ret = dfs(b, depth - 1, k);

    temp = b.map[py][px];
    b.map[py][px] = b.map[ty][tx];
    b.map[ty][tx] = temp;
    if (ret != -1)
      return ret;
  }
  return -1;
}

int main(int argc, char const *argv[]) {
  BOARD b;
  for (int i = 0; i < boardw; ++i) {
    for (int j = 0; j < boardw; ++j) {
      cin >> b.map[i][j];
    }
  }
  if (check(b)) {
    cout << 0 << endl;
    return 0;
  }
  for (int i = 1; i <= 45; i++) {
    int ret = dfs(b, i, -1);
    if (ret == 1) {
      cout << i << endl;
      return 0;
    }
  }

  return 0;
}