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

#include <bits/stdc++.h>

#define reps(i, s, n) for (int i = (s); i < (n); i++)
#define rep(i, n) reps(i, 0, n)
#define rrep(i, n) for (int i = n - 1; i >= 0; i--)
#define X first
#define Y second
#define pb push_back

using namespace std;
typedef long long ll;
typedef pair<int, int> pii;

const ll INF = 1e9;

struct dice {
  int d[6];
  int point() { return d[0]; }
  void set(int l, int r, int f, int b, int _d, int u) {
    d[3] = l;
    d[1] = r;
    d[4] = f;
    d[5] = b;
    d[0] = _d;
    d[2] = u;
  }
};

void rot(dice &dc, pii &pos, char r) {
  if (r == 'L') {
    swap(dc.d[0], dc.d[3]);
    swap(dc.d[3], dc.d[2]);
    swap(dc.d[2], dc.d[1]);
    pos.X--;
  } else if (r == 'R') {
    swap(dc.d[0], dc.d[1]);
    swap(dc.d[1], dc.d[2]);
    swap(dc.d[2], dc.d[3]);
    pos.X++;
  } else if (r == 'F') {
    swap(dc.d[0], dc.d[4]);
    swap(dc.d[4], dc.d[2]);
    swap(dc.d[2], dc.d[5]);
    pos.Y--;
  } else if (r == 'B') {
    swap(dc.d[0], dc.d[5]);
    swap(dc.d[5], dc.d[2]);
    swap(dc.d[2], dc.d[4]);
    pos.Y++;
  }
}

dice dice_org[20];
pii dice_pos[20];
string dice_rot[20];
map<pii, int> tb[20];
void rots(int n) {
  dice dc = dice_org[n];
  pii pos = dice_pos[n];
  // pre
  tb[n][pii(pos.X, pos.Y)] = dc.point();
  for (auto c : dice_rot[n]) {
    rot(dc, pos, c);
    tb[n][pii(pos.X, pos.Y)] = dc.point();
  }
}

int solve(map<pii, int> &table, int n, bool update = false) {
  // merge
  int sum = 0;
  for (auto p : tb[n])
    if (table.count(p.X) == 0) {
      if (update)
        table[p.X] = p.Y;
      sum += p.Y;
    }
  return sum;
}

map<pii, int> tables[1 << 20];
int main() {
  int N;
  while (cin >> N, N) {
    rep(i, N) {
      int x, y;
      cin >> x >> y;
      x += 2000;
      y += 2000;
      dice_pos[i].X = x;
      dice_pos[i].Y = y;

      int l, r, f, b, d, u;
      cin >> l >> r >> f >> b >> d >> u;
      dice_org[i].set(l, r, f, b, d, u);

      cin >> dice_rot[i];
    }

    rep(i, N) {
      tb[i].clear();
      rots(i);
    }
    rep(i, 1 << 20) tables[i].clear();

    int dp[1 << 20] = {};
    rep(i, 1 << N) {
      auto table = tables[i];
      rep(k, N) {
        int nx = (1 << k) | i;
        if (nx != i) {
          if (tables[nx].empty()) {
            dp[nx] = max(dp[nx], dp[i] + solve(table, k, true));
            tables[nx] = table;
            table = tables[i];
          } else {
            dp[nx] = max(dp[nx], dp[i] + solve(table, k));
          }
        }
      }
      tables[i].clear();
    }
    cout << dp[(1 << N) - 1] << endl;
  }
  return 0;
}

Error: TLE

Fixed submission:

#include <bits/stdc++.h>

#define reps(i, s, n) for (int i = (s); i < (n); i++)
#define rep(i, n) reps(i, 0, n)
#define rrep(i, n) for (int i = n - 1; i >= 0; i--)
#define X first
#define Y second
#define pb push_back

using namespace std;
typedef long long ll;
typedef pair<int, int> pii;

const ll INF = 1e9;

struct dice {
  int d[6];
  int point() { return d[0]; }
  void set(int l, int r, int f, int b, int _d, int u) {
    d[3] = l;
    d[1] = r;
    d[4] = f;
    d[5] = b;
    d[0] = _d;
    d[2] = u;
  }
};

void rot(dice &dc, pii &pos, char r) {
  if (r == 'L') {
    swap(dc.d[0], dc.d[3]);
    swap(dc.d[3], dc.d[2]);
    swap(dc.d[2], dc.d[1]);
    pos.X--;
  } else if (r == 'R') {
    swap(dc.d[0], dc.d[1]);
    swap(dc.d[1], dc.d[2]);
    swap(dc.d[2], dc.d[3]);
    pos.X++;
  } else if (r == 'F') {
    swap(dc.d[0], dc.d[4]);
    swap(dc.d[4], dc.d[2]);
    swap(dc.d[2], dc.d[5]);
    pos.Y--;
  } else if (r == 'B') {
    swap(dc.d[0], dc.d[5]);
    swap(dc.d[5], dc.d[2]);
    swap(dc.d[2], dc.d[4]);
    pos.Y++;
  }
}

dice dice_org[20];
pii dice_pos[20];
string dice_rot[20];
map<pii, int> tb[20];
void rots(int n) {
  dice dc = dice_org[n];
  pii pos = dice_pos[n];
  // pre
  tb[n][pii(pos.X, pos.Y)] = dc.point();
  for (auto c : dice_rot[n]) {
    rot(dc, pos, c);
    tb[n][pii(pos.X, pos.Y)] = dc.point();
  }
}

int solve(map<pii, int> &table, int n) {
  // merge
  int sum = 0;
  for (auto p : tb[n])
    if (table.count(p.X) == 0) {
      table[p.X] = p.Y;
      sum += p.Y;
    }
  return sum;
}

map<pii, int> tables[1 << 20];
int main() {
  int N;
  while (cin >> N, N) {
    rep(i, N) {
      int x, y;
      cin >> x >> y;
      x += 2000;
      y += 2000;
      dice_pos[i].X = x;
      dice_pos[i].Y = y;

      int l, r, f, b, d, u;
      cin >> l >> r >> f >> b >> d >> u;
      dice_org[i].set(l, r, f, b, d, u);

      cin >> dice_rot[i];
    }

    rep(i, N) {
      tb[i].clear();
      rots(i);
    }
    rep(i, 1 << 20) tables[i].clear();

    int dp[1 << 20] = {};
    rep(i, 1 << N) {
      rep(k, N) {
        int nx = (1 << k) | i;
        if (nx != i) {
          auto table = tables[i];
          dp[nx] = max(dp[nx], dp[i] + solve(table, k));
          if (tables[nx].empty()) {
            tables[nx] = table;
          }
        }
      }
      tables[i].clear();
    }
    cout << dp[(1 << N) - 1] << endl;
  }
  return 0;
}