社区讨论
求问玄关
P2704[NOI2001] 炮兵阵地参与者 7已保存回复 15
讨论操作
快速查看讨论及其快照的属性,并进行相关操作。
- 当前回复
- 14 条
- 当前快照
- 1 份
- 快照标识符
- @mj8ph2ds
- 此快照首次捕获于
- 2025/12/16 22:56 2 个月前
- 此快照最后确认于
- 2025/12/19 23:00 2 个月前
先贴代码:
CPP#include <bits/stdc++.h>
using namespace std;
int n,m,can[110][4200],num[110],maxs[110],f[110][2100][2100],ans,cnt[2100];
char a[110][7 + 8];
int main(){
ios::sync_with_stdio(0);cin.tie(0);
cin >> n >> m;
for(int i = 1;i <= n;i ++)
for(int j = 1;j <= m;j ++)
cin >> a[i][j];
for(int i = 1;i <= n;i ++)
for(int j = m;j >= 1;j --)
if(a[i][j] == 'P') maxs[i] += (1 << (m - j));
for(int i = 1;i <= (1 << 10) + 5;i ++){
int x = 1;
while(x <= i){
if(x & i) cnt[i] ++;
x <<= 1;
}
}
for(int i = 1;i <= n;i ++){
for(int j = maxs[i];;j = maxs[i] & (j - 1)){
if(!((j << 2) & j) && !((j << 1) & j)) can[i][++ num[i]] = j;
if(!j) break;
}
}
for(int i = 1;i <= n;i ++){
for(int j = 1;j <= num[i];j ++){
int state = can[i][j];
if(i == 1){
f[i][state][0] = max(f[i][state][0],cnt[state]);
continue;
}
for(int k = 1;k <= num[i - 1];k ++){ //枚举上一行
int lst_state = can[i - 1][k];
if(i > 1 && (state & lst_state)) continue;
if(i == 2){
f[i][state][lst_state] = max(f[i][state][lst_state],cnt[state] + cnt[lst_state]);
continue;
}
for(int o = 1;o <= num[i - 2];o ++){
int lst_bf_state = can[i - 2][o];
if(i > 2 && (state & lst_bf_state)) continue;
if(i > 2 && (lst_state & lst_bf_state)) continue;
f[i][state][lst_state] = max(f[i - 1][lst_state][lst_bf_state] + cnt[state],f[i][state][lst_state]);
}
}
}
}
for(int i = 0;i <= (1 << 10) + 5;i ++){
for(int j = 0;j <= (1 << 10) + 5;j ++){
ans = max(ans,f[n][i][j]);
}
}
cout << ans;
}
代码中定义了一个很大的数组
f[110][2100][2100],按理来说它占用了 很明显会爆空间,但是交上去并不会,甚至最多只用了 的空间。提交记录:https://www.luogu.com.cn/record/253570956
我看到很多题解都用了滚动数组优化,所以说是我的代码有误,还是计算占用空间的方法错了,亦或说这道题使用滚动数组优化是不必要的?
回复
共 15 条回复,欢迎继续交流。
正在加载回复...