AcWing 1064.小国王(状压dp)
作者:
冰冷酒
,
2022-05-16 23:44:20
,
所有人可见
,
阅读 209
#include <bits/stdc++.h>
using namespace std;
typedef long long LL;
typedef unsigned long long ULL;
typedef pair<int, int> PII;
const int N = 12, M = 1 << 10, K = 110;
vector<int> state;
vector<int> head[M];
int cnt[M];
LL f[N][K][M];
int n, m;
bool check(int x)
{
for (int i = 0; i < n; i ++)
if ((x >> i & 1) && (x >> i + 1 & 1))
return false;
return true;
}
int count(int x)
{
int res = 0;
for (int i = 0; i < n; i ++) res += x >> i & 1;
return res;
}
int main()
{
ios::sync_with_stdio(false), cin.tie(0), cout.tie(0);
cin >> n >> m;
for (int i = 0; i < 1 << n; i ++)
if (check(i))
{
cnt[i] = count(i);
state.push_back(i);
}
for (int i = 0; i < state.size(); i ++)
for (int j = 0; j < state.size(); j ++)
{
int a = state[i], b = state[j];
if ((a & b) == 0 && (check(a | b)))
head[i].push_back(j);
}
f[0][0][0] = 1;
for (int i = 1; i <= n + 1; i ++)
for (int j = 0; j <= m; j ++)
for (int a = 0; a < state.size(); a ++)
for (auto b : head[a])
{
int c = cnt[state[a]];
if (j >= c) f[i][j][a] += f[i - 1][j - c][b];
}
cout << f[n + 1][m][0] << '\n';
return 0;
}