luogu Eat the Trees
Posted luoyibujue
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了luogu Eat the Trees相关的知识,希望对你有一定的参考价值。
/*
用和模板类似的方法就行
但是实际上弱化版不用考虑匹配情况限制更加宽松, 只需要保存每个位置有无插头即可,
*/
#include<cstdio>
#include<algorithm>
#include<cstring>
#include<iostream>
#include<queue>
#include<cmath>
#define ll long long
#define M 13
#define mmp make_pair
using namespace std;
int read() {
int nm = 0, f = 1;
char c = getchar();
for(; !isdigit(c); c = getchar()) if(c == '-') f = -1;
for(; isdigit(c); c = getchar()) nm = nm * 10 + c - '0';
return nm * f;
}
const int hs = 299987;
int mp[M][M], ex, ey, now, last, bit[30], g[2][300010], tot[2], n, m;
ll ans, f[2][300010];
struct Note {
int nxt, to;
} note[300010];
int head[300010], cnt = 0;
void insert(int x, ll v) {
int key = x % hs;
for(int i = head[key]; i; i = note[i].nxt) {
if(g[now][note[i].to] == x) {
f[now][note[i].to] += v;
return;
}
}
tot[now]++;
g[now][tot[now]] = x;
f[now][tot[now]] = v;
note[++cnt].nxt = head[key];
head[key] = cnt;
note[cnt].to = tot[now];
}
void Dp() {
now = 1, last = 0;
tot[now] = 1;
f[now][1] = 1;
g[now][1] = 0;
for(int i = 1; i <= n; i++) {
for(int j = 1; j <= tot[now]; j++) g[now][j] <<= 1;
for(int j = 1; j <= m; j++) {
cnt = 0;
memset(head, 0, sizeof(head));
swap(now, last);
tot[now] = 0;
ll nowans;
int nowsta, sd, sr;
for(int k = 1; k <= tot[last]; k++) {
nowsta = g[last][k], nowans = f[last][k];
sd = (nowsta >> bit[j]) % 2, sr = (nowsta >> bit[j - 1]) % 2;
if(!mp[i][j]) {
if(!sd && !sr) insert(nowsta, nowans);
} else if(!sd && !sr) {
if(mp[i + 1][j] && mp[i][j + 1]) insert(nowsta + (1 << bit[j - 1]) + (1 << bit[j]), nowans);
} else if(!sd && sr) {
if(mp[i + 1][j]) insert(nowsta, nowans);
if(mp[i][j + 1]) insert(nowsta - (1 << bit[j - 1]) + (1 << bit[j]), nowans);
} else if(sd && !sr) {
if(mp[i + 1][j]) insert(nowsta - (1 << bit[j]) + (1 << bit[j - 1]), nowans);
if(mp[i][j + 1]) insert(nowsta, nowans);
} else {
insert(nowsta - (1 << bit[j]) - (1 << bit[j - 1]), nowans);
if(i == ex && j == ey) ans += nowans;
}
}
}
}
}
void init() {
ans = 0;
ex = 0, ey = 0;
memset(f, 0, sizeof(f));
memset(g, 0, sizeof(g));
memset(mp, 0, sizeof(mp));
}
int main() {
int T = read();
for(int i = 1; i <= 25; i++) bit[i] = i;
while(T--) {
init();
n = read(), m = read();
for(int i = 1; i <= n; i++) {
for(int j = 1; j <= m; j++) {
int x = read();
if(x == 1) mp[i][j] = 1, ex = i, ey = j;
}
}
Dp();
if(ex == 0 && ey == 0) ans++;
cout << ans << '
';
}
return 0;
}
/*
2
2 4
1 1 1 1
1 1 1 1
6 3
1 1 1
1 0 1
1 1 1
1 1 1
1 0 1
1 1 1
1
3 3
0 0 0
0 0 0
0 0 0
*/
以上是关于luogu Eat the Trees的主要内容,如果未能解决你的问题,请参考以下文章