洛谷 P3930 SAC E#1

编程入门 行业动态 更新时间:2024-10-28 11:34:16

<a href=https://www.elefans.com/category/jswz/34/1769987.html style=洛谷 P3930 SAC E#1"/>

洛谷 P3930 SAC E#1

这题,又是一道卡内存的shabby题。
一眼看,广搜,加个状态记录哪些黑子已经被消灭了,十分套路。f[x][y][p]表示,走到(x,y),黑子被消灭的状态是p的最小步数。可是, 50*50 *1<<16 ,这个数组,貌似500MB也不太够,现在就来优化一下这个内存吧。
由于每次的步数增加都是1,所以,在广搜中,可以保证,队列前面的值小于等于队列后面的值,所以,对于一个[x][y][p](意思就是:现在的位置,消灭的黑子)的状态来说,当它出现第一次的时候,它的步数值,一定已经是最优的了,后面是不会更新到比它此刻的值还要优的值了的,所以,对于f[x][y][p]来说,不会出现第二次f[x][y][p]>f[nowx][nowy][nowp]+1的情况了,所以,f数组只会更新一次,那么就可以用bool来存储是否更新过了,然后在queue中,新增加一个dis值,就可以了。比原来的int小4倍内存。
现在可能有人会问,那queue里面增加了一个dis值会不会导致炸内存呢?我有个同学就说他queue炸内存了。其实是因为他写挂了,状态冗余导致的。每次取出一个值,然后再放进去最多8个值(而这8个值,可能远远不会到),是基本不会是的queue炸内存的。这样,就把f数组成功给优化了。
除了内存这个坑点加麻烦点意外,别的就是纯码量了,我的代码写的比较傻,会有一个比较大的常数,因为有很多无用判断都可以省略,但我没省略。但是,还是跑的挺快的。
没省略的原因有二:1.全部写上不用动脑子想哪些需要省略哪些不需要省略,提供正确率,节省时间;2.使得代码比较对称,长的代码,如果对称了,就有层次感,无论是自己检查起来还是别人看起来都更加方便。
#include <bits/stdc++.h>
using namespace std;
const int dx[8]={-1,-2,-2,-1,1,2,2,1},dy[8]={-2,-1,1,2,-2,-1,1,2};
const int N=60;
int n,cnt,sx,sy,tx,ty,max_statue;
int mp[N][N];
bool f[N][N][1<<16];
char str[N][N];
struct number{int x,y; char id;}num[N*N];
struct node{int x,y,p,dis;};inline bool pd(int x,int y,int p)
{int x1,y1;if (x<1 || x>n || y<1 || y>n) return false;int xx,yy;char id;for (register int i=1; i<=cnt; ++i)if (!((1<<(i-1))&p)){xx=num[i].x; yy=num[i].y; id=num[i].id;if (xx==x && yy==y) continue; //如果把这个棋子吃了,就OK了 if (id=='C')   //有阻挡 {x1=xx; y1=yy;while (x1-1>=1){x1--;if (mp[x1][y1]){if (!((1<<(mp[x1][y1]-1))&p)) break;}if (x1==x && y1==y) return false;	}x1=xx; y1=yy;while (x1+1<=n){x1++;if (mp[x1][y1]){if (!((1<<(mp[x1][y1]-1))&p)

更多推荐

洛谷 P3930 SAC E#1

本文发布于:2024-02-12 00:13:42,感谢您对本站的认可!
本文链接:https://www.elefans.com/category/jswz/34/1684521.html
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。
本文标签:洛谷   SAC

发布评论

评论列表 (有 0 条评论)
草根站长

>www.elefans.com

编程频道|电子爱好者 - 技术资讯及电子产品介绍!