您的位置:首页 > 其它

noip2011提高组——mayan游戏

2015-02-08 10:12 357 查看
这道题看了 除了暴力dfs +模拟 真的找不到其他思路了

再一看 dfs深度最多才5 棋盘7 *5 业界良心。。

而且格子也只有左右移动

暴力dfs 就是干。。。

当然纯暴力当然不行的 不然怎么做noipday1压轴题啊、、

一定要剪枝

因为向右移动优先于向左移动

我只剪了一个枝 就是当 一个格子向左移动的时候 如果左边有一个值 就pass掉

因为这个格子向左移 等于 上一个格子向右移 重复了O(∩_∩)O~

还要注意 这个题一般的dfs回溯(通过纯递归)

是行不通的 因为这过程中有消除和掉落的操作 执行了之后就无法回到上一步

所以要么用结构体数组 储存状态(这种要把结构体数组开大点 免得状态太多爆掉)

或者是用栈结构(这个比较省空间 我用的栈)实现dfs

好了 剪了枝就是看dfs+模拟能力和 代码能力了。。。

有一个坑了我很久的是 在设置“掉下”这个操作的时候

掉下到了0就要特判了 我开始没有 特判 出现了负数下标 就程序崩溃 乱赋值了。。。QAQ

#include<iostream>
#include<cstdio>
#include<stack>
#include<algorithm>
#include<cstring>
using namespace std;
int n;
int now;
int mac;
struct state
{
int col[11];
int step;
int map[5][7];
int stepx[6];
int stepy[6];
int cz[6];
}cs,ns,start;
stack<state>s;
void readdata()
{
scanf("%d",&n);
for(int i=0;i<=4;i++)
for(int j=0;j<=7;j++)
{
scanf("%d",&cs.map[i][j]);
if(cs.map[i][j]==0)
break;
cs.col[cs.map[i][j]]++;
mac=max(mac,cs.map[i][j]);
}
}
void deal()
{
int lef=0;
for(int i=1;i<=mac;i++)
lef+=ns.col[i];
if(lef!=0)
return;
for(int i=1;i<=n;i++)
printf("%d %d %d\n",ns.stepx[i],ns.stepy[i],ns.cz[i]);
exit(0);
}
bool drop()
{
bool ret=false;
for(int i=0;i<=4;i++)
for(int j=0;j<=5;j++)
{
int xx=i;
int yy=j;
while(ns.map[xx][yy]==0&&ns.map[xx][yy+1]!=0)
{
int tt=ns.map[xx][yy];
ns.map[xx][yy]=ns.map[xx][yy+1];
ns.map[xx][yy+1]=tt;
ret=true;
yy--;
if(yy<0)
break;
}
}
return ret;
}
bool clear()
{
bool ret=false;
bool cle[5][7];
memset(cle,0,sizeof(cle));
for(int i=0;i<=4;i++)//横向消除
for(int j=0;j<=4;j++)
{
if(((ns.map[i][j]==ns.map[i][j+1])&&(ns.map[i][j+1]==ns.map[i][j+2]))&&ns.map[i][j]!=0)
{
cle[i][j]=cle[i][j+1]=cle[i][j+2]=true;
ret=true;
}
}
for(int i=0;i<=2;i++)//纵向消除
for(int j=0;j<=6;j++)
{
if(((ns.map[i+1][j]==ns.map[i+2][j])&&(ns.map[i+1][j]==ns.map[i][j]))&&ns.map[i][j]!=0)
{
cle[i][j]=cle[i+1][j]=cle[i+2][j]=true;
ret=true;
}
}
for(int i=0;i<=4;i++)
for(int j=0;j<=6;j++)
{
if(cle[i][j])
{
ns.col[ns.map[i][j]]--;
ns.map[i][j]=0;
}
}
return ret;
}
void solve()
{
while(1)
{
bool b1=drop();
bool b2=clear();
if((!b1)&&(!b2))
break;
}
}
void dfs()
{
for(int i=0;i<=4;i++)
for(int j=0;j<=6;j++)
for(int k=1;k<=2;k++)
{
if(!s.empty())
cs=s.top();
else cs=start;
ns=cs;
now=k==1?k:-1;
if(ns.map[i][j]==0)
continue;
if(i+now>4||i+now<0)
continue;
if(ns.map[i+now][j]!=0&&now==-1)
continue;
int t=ns.map[i+now][j];
ns.map[i+now][j]=ns.map[i][j];
ns.map[i][j]=t;
ns.step++;
ns.stepx[ns.step]=i;
ns.stepy[ns.step]=j;
ns.cz[ns.step]=now;
solve();
if(ns.step>=n)
{
deal();
continue;
}
s.push(ns);
dfs();
s.pop();
}
}
int main()
{
readdata();
start=cs;
dfs();
printf("-1\n");
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: