Problem p03222 (C++)

Buggy submission (status: Runtime Error):
#include <algorithm>
#include <array>
#include <cstdio>
#include <iostream>
#include <map>
#include <math.h>
#include <numeric>
#include <sstream>
#include <string.h>
#include <string>
#include <unistd.h>
#include <vector>
#define ALL(a) (a).begin(), (a).end()
const long long INF = 1LL << 58;
const long long MOD = 1e9 + 7;

using namespace std;
typedef long long ll;
struct point {
  int x;
  int y;
};
int gcd(int a, int b) {
  if (a > b) {
    return gcd(b, a);
  }
  return a == 0 ? b : gcd(b % a, a);
}
int lcm(int m, int n) {
  // 引数に０がある場合は０を返す
  if ((0 == m) || (0 == n))
    return 0;

  return ((m / gcd(m, n)) * n); // lcm = m * n / gcd(m,n)
} // lcm
int input() {
  int x;
  cin >> x;
  return x;
}

int moji(char in) {
  int ans = (int)in - (int)'a';
  if ((ans < 0) || (ans > 25)) {
    ans = 26;
  }
  return ans;
}
const int VV = 10; // 場合に応じてVVの値のみ変更する必要あり
// dijkstra(s)sがスタート地点でそこからの最短距離を配列dで表す。正の重みのみ使用可能
int cost[VV][VV];
int d[VV];
bool used[VV];
void dijkstra(int s) {
  fill(d, d + VV, 100000);
  fill(used, used + VV, false);
  d[s] = 0;
  while (true) {
    int v = -1;
    for (int u = 0; u < VV; u++) {
      if (!used[u] && (v == -1 || d[u] < d[v]))
        v = u;
    }
    if (v == -1)
      break;
    used[v] = true;
    for (int u = 0; u < VV; u++) {
      d[u] = min(d[u], d[v] + cost[v][u]);
    }
  }
}

int compare_int(const void *a, const void *b) // qsort(quick sort利用時に使用)
{
  return *(int *)a - *(int *)b;
}

int binary_searchh(long long x, long long k[], int n) {
  int l = 0;
  int r = n;
  while (r - l >= 1) {
    int i = (l + r) / 2;
    if (k[i] == x)
      return i;
    else if (k[i] < x)
      l = i + 1;
    else
      r = i;
  }
  return -1;
}

struct File {
  int aa;
  int bb;

  File(const int &aa, const int &bb) : aa(aa), bb(bb) {}
};

bool operator<(const File &a, const File &b) {
  // ファイル種別、ファイル名の順番で優先順位を付けて比較
  return std::tie(a.aa, a.bb) < std::tie(b.aa, b.bb);
}

long long kaijo(long long x) {
  long long l = 10 * 10 * 10 * 10 * 10 * 10 * 10 * 10 * 10 + 7;
  long long sum = 1;
  for (int i = x; i > 0; i--) {
    sum *= i;
    if (sum > l) {
      sum %= l;
    }
  }
  return sum;
}

template <class T> void chmin(T &a, T b) {
  if (a > b) {
    a = b;
  }
}

// formerは前方のindex(自分自身を含んで良い)
template <class T> int former(const vector<T> &v, T x) {
  return upper_bound(v.begin(), v.end(), x) - v.begin() - 1;
}
// latterは後方のindex(自分自身を含んで良い)
template <class T> int latter(const vector<T> &v, T x) {
  return lower_bound(v.begin(), v.end(), x) - v.begin();
}

int main() {
  int H, W, K;
  cin >> H >> W >> K;
  K--;
  long long dp[H + 1][W];
  for (int i = 0; i < H + 1; i++) {
    for (int j = 0; j < W; j++) {
      dp[i][j] = 0;
    }
  }
  dp[0][0] = 1;
  for (int h = 0; h < H + 1; h++) {
    for (int b = 0; b < (1 << (W - 1)); b++) {
      bool ok = true;
      for (int x = 0; x < W - 2; x++) {
        if ((b >> x) % 4 == 3) {
          ok = false;
          break;
        }
      }
      if (!ok) {
        continue;
      }
      int hh[W];
      for (int i = 0; i < W; i++) {
        hh[i] = i;
      }
      for (int i = 0; i < W - 1; i++) {
        if (b & (1 << i)) {
          swap(hh[i], hh[i + 1]);
        }
      }
      for (int i = 0; i < W; ++i) {
        dp[h + 1][hh[i]] += dp[h][i];
        dp[h + 1][hh[i]] %= MOD;
      }
    }
  }
  cout << dp[H][K] << endl;
}


Fixed submission:
#include <algorithm>
#include <array>
#include <cstdio>
#include <iostream>
#include <map>
#include <math.h>
#include <numeric>
#include <sstream>
#include <string.h>
#include <string>
#include <unistd.h>
#include <vector>
#define ALL(a) (a).begin(), (a).end()
const long long INF = 1LL << 58;
const long long MOD = 1e9 + 7;

using namespace std;
typedef long long ll;
struct point {
  int x;
  int y;
};
int gcd(int a, int b) {
  if (a > b) {
    return gcd(b, a);
  }
  return a == 0 ? b : gcd(b % a, a);
}
int lcm(int m, int n) {
  // 引数に０がある場合は０を返す
  if ((0 == m) || (0 == n))
    return 0;

  return ((m / gcd(m, n)) * n); // lcm = m * n / gcd(m,n)
} // lcm
int input() {
  int x;
  cin >> x;
  return x;
}

int moji(char in) {
  int ans = (int)in - (int)'a';
  if ((ans < 0) || (ans > 25)) {
    ans = 26;
  }
  return ans;
}
const int VV = 10; // 場合に応じてVVの値のみ変更する必要あり
// dijkstra(s)sがスタート地点でそこからの最短距離を配列dで表す。正の重みのみ使用可能
int cost[VV][VV];
int d[VV];
bool used[VV];
void dijkstra(int s) {
  fill(d, d + VV, 100000);
  fill(used, used + VV, false);
  d[s] = 0;
  while (true) {
    int v = -1;
    for (int u = 0; u < VV; u++) {
      if (!used[u] && (v == -1 || d[u] < d[v]))
        v = u;
    }
    if (v == -1)
      break;
    used[v] = true;
    for (int u = 0; u < VV; u++) {
      d[u] = min(d[u], d[v] + cost[v][u]);
    }
  }
}

int compare_int(const void *a, const void *b) // qsort(quick sort利用時に使用)
{
  return *(int *)a - *(int *)b;
}

int binary_searchh(long long x, long long k[], int n) {
  int l = 0;
  int r = n;
  while (r - l >= 1) {
    int i = (l + r) / 2;
    if (k[i] == x)
      return i;
    else if (k[i] < x)
      l = i + 1;
    else
      r = i;
  }
  return -1;
}

struct File {
  int aa;
  int bb;

  File(const int &aa, const int &bb) : aa(aa), bb(bb) {}
};

bool operator<(const File &a, const File &b) {
  // ファイル種別、ファイル名の順番で優先順位を付けて比較
  return std::tie(a.aa, a.bb) < std::tie(b.aa, b.bb);
}

long long kaijo(long long x) {
  long long l = 10 * 10 * 10 * 10 * 10 * 10 * 10 * 10 * 10 + 7;
  long long sum = 1;
  for (int i = x; i > 0; i--) {
    sum *= i;
    if (sum > l) {
      sum %= l;
    }
  }
  return sum;
}

template <class T> void chmin(T &a, T b) {
  if (a > b) {
    a = b;
  }
}

// formerは前方のindex(自分自身を含んで良い)
template <class T> int former(const vector<T> &v, T x) {
  return upper_bound(v.begin(), v.end(), x) - v.begin() - 1;
}
// latterは後方のindex(自分自身を含んで良い)
template <class T> int latter(const vector<T> &v, T x) {
  return lower_bound(v.begin(), v.end(), x) - v.begin();
}

int main() {
  int H, W, K;
  cin >> H >> W >> K;
  K--;
  long long dp[H + 1][W];
  for (int i = 0; i < H + 1; i++) {
    for (int j = 0; j < W; j++) {
      dp[i][j] = 0;
    }
  }
  dp[0][0] = 1;
  for (int h = 0; h < H; h++) {
    for (int b = 0; b < (1 << (W - 1)); b++) {
      bool ok = true;
      for (int x = 0; x < W - 2; x++) {
        if ((b >> x) % 4 == 3) {
          ok = false;
          break;
        }
      }
      if (!ok) {
        continue;
      }
      int hh[W];
      for (int i = 0; i < W; i++) {
        hh[i] = i;
      }
      for (int i = 0; i < W - 1; i++) {
        if (b & (1 << i)) {
          swap(hh[i], hh[i + 1]);
        }
      }
      for (int i = 0; i < W; ++i) {
        dp[h + 1][hh[i]] += dp[h][i];
        dp[h + 1][hh[i]] %= MOD;
      }
    }
  }
  cout << dp[H][K] << endl;
}