POJ 1198/HDU 1401
双向广搜。。。
呃,双向广搜一般都都用了HASH判重,这样可以更快判断两个方向是否重叠了。这道题用了双向的BFS,有效地减少了状态。但代码太长了,不写,贴一个别人的代码。。
#include<iostream>
#include<set>
#include<queue>
#include<algorithm>
using namespace std; typedef __int64 i64; const i64 one = (i64);
const int maxn = << ;
int dx[] = { , ,- , } ;
int dy[] = { , , , - }; struct node
{
i64 bd;
int pos[];
}; node st , ed ; i64 stq[maxn] ,edq[maxn] , sz ,ez ; set<i64> win ;
set<i64>:: iterator it ; bool IsOut( int cx,int cy)
{
return cx < || cy < || cx >= || cy >= ;
} bool IsOn( i64 bd ,int cx, int cy)
{
return bd & ( one<<(cx * + cy) ) ;
} void clr( i64 &bd ,int i)
{
if( ! IsOn( bd , i/ , i%) ) return ;
bd -= one<<i;
} void put( i64 &bd, int i )
{
if(IsOn(bd ,i/ ,i%) ) return ;
bd += one <<i ;
} bool next(node cur, int i,int j , node &son)
{
int t , tx , ty , nx , ny , cx , cy ;
i64 bd = cur.bd;
t = cur.pos[i] , tx = t / , ty = t % ;
nx = tx + dx[j] , ny = ty + dy[j] ;
if( IsOut(nx, ny) ) return false;
if( IsOn (bd , nx, ny) )
{
cx = *nx - tx, cy = *ny - ty;
if( IsOut(cx , cy) || IsOn(bd , cx , cy) ) return false;
clr(cur.bd, tx* + ty);
put(cur.bd, cx* + cy);
cur.pos[i] = cx * + cy;
son = cur;
return true;
}
clr(cur.bd , tx * + ty); put(cur.bd , nx * + ny);
cur.pos[i] = nx * + ny ;
son = cur;
return true;
} void deal(node bgn )
{
int i , j , dep = ;
node cur , son , tail;
queue<node> q; tail.bd = - ;
win.clear(); win.insert(bgn.bd);
q.push(tail); q.push(bgn);
while(!q.empty())
{
cur = q.front(); q.pop();
if( cur.bd == - )
{
if(q.empty()) return ;
q.push(tail); cur = q.front() ; q.pop();
if( ++ dep > ) return ;
}
for(i = ; i < ;++i)
for( j = ;j < ;++j )
if ( next( cur , i , j , son ) )
if( win.find(son.bd) ==win.end() )
{
q.push(son);
win.insert(son.bd);
}
}
} int bbs(i64 x)
{
int l , r ,mid;
l = , r = ez - ;
while(l <= r)
{
mid = ( l + r) / ;
if(edq[ mid ] == x) return mid ;
else if ( x < edq[mid] ) r = mid - ;
else l = mid + ;
}
return -;
} bool can()
{
int i , x[],y[] ,check ;
if(scanf("%d%d%d%d%d%d%d%d",&x[],&y[],&x[],&y[],&x[],&y[],&x[],&y[]) == EOF )
return false;
st.bd = ;
for(i = ; i< ; ++i)
{
-- x[i] , -- y[i] ;
put(st.bd , x[i] * + y[i]);
st.pos[i] = x[i] * + y[i];
} ed.bd = ;
for(i = ; i< ; ++i)
{
scanf("%d%d",&x[i],&y[i]);
-- x[i] , -- y[i];
put(ed.bd , x[i] * + y[i]);
ed.pos[i] = x[i] * + y[i] ;
} sz = ez = ; deal(st);
for(it = win.begin() ; it!=win.end(); it ++ )
stq[sz ++ ] = *it; deal(ed);
for(it = win.begin() ; it!=win.end(); it++)
edq[ez ++ ] = *it ; sort(edq , edq + ez); check = ;
for(i = ; i < sz && !check ; ++i)
if( bbs(stq[i]) !=- )
check = ; if(check)
cout<<"YES"<<endl;
else
cout<<"NO"<<endl;
return true;
} int main()
{
while(can());
return ;
}
POJ 1198/HDU 1401的更多相关文章
- poj 1198 hdu 1401 搜索+剪枝 Solitaire
写到一半才发现能够用双向搜索4层来写,但已经不愿意改了,干脆暴搜+剪枝水过去算了. 想到一个非常水的剪枝,h函数为 当前点到终点4个点的最短距离加起来除以2.由于最多一步走2格,然后在HDU上T了, ...
- POJ 1198 / HDU 1401 Solitaire (记忆化搜索+meet in middle)
题目大意:给你一个8*8的棋盘,上面有四个棋子,给你一个初始排布,一个目标排布,每次移动,可以把一个棋子移动到一个相邻的空位,或者跨过1个相邻的棋子,在保证棋子移动不超过8次的情况下,问能否把棋盘上的 ...
- POJ 2104&HDU 2665 Kth number(主席树入门+离散化)
K-th Number Time Limit: 20000MS Memory Limit: 65536K Total Submissions: 50247 Accepted: 17101 Ca ...
- poj 1251 poj 1258 hdu 1863 poj 1287 poj 2421 hdu 1233 最小生成树模板题
poj 1251 && hdu 1301 Sample Input 9 //n 结点数A 2 B 12 I 25B 3 C 10 H 40 I 8C 2 D 18 G 55D 1 E ...
- Eight POJ - 1077 HDU - 1043 八数码
Eight POJ - 1077 HDU - 1043 八数码问题.用hash(康托展开)判重 bfs(TLE) #include<cstdio> #include<iostream ...
- HDU 1401 Solitaire 双向DFS
HDU 1401 Solitaire 双向DFS 题意 给定一个\(8*8\)的棋盘,棋盘上有4个棋子.每一步操作可以把任意一个棋子移动到它周围四个方向上的空格子上,或者可以跳过它四个方向上的棋子(就 ...
- POJ 1177/HDU 1828 picture 线段树+离散化+扫描线 轮廓周长计算
求n个图矩形放下来,有的重合有些重合一部分有些没重合,求最后总的不规则图型的轮廓长度. 我的做法是对x进行一遍扫描线,再对y做一遍同样的扫描线,相加即可.因为最后的轮廓必定是由不重合的线段长度组成的, ...
- POJ 1308&&HDU 1272 并查集判断图
HDU 1272 I - 小希的迷宫 Time Limit:1000MS Memory Limit:32768KB 64bit IO Format:%I64d & %I64 ...
- POJ 1077 && HDU 1043 Eight A*算法,bfs,康托展开,hash 难度:3
http://poj.org/problem?id=1077 http://acm.hdu.edu.cn/showproblem.php?pid=1043 X=a[n]*(n-1)!+a[n-1]*( ...
随机推荐
- IJ:ALI OSS 配置
ylbtech-IJ:ALI OSS 配置 1. src/resources/返回顶部 1.src/resources/ 1.1.aliyunoss.properties # oss\u7684\u5 ...
- bzoj1895
fhqtreap 其实fhqtreap只有可持久化之后才用新建节点... reverse和splay一样. //#include<bits/stdc++.h> #include<cs ...
- Django day04 路由控制
Django请求的整个的生命周期 Django中路由控制的作用: 一: 简单配置 url 是一个函数 -第一个参数是正则表达式(如果要精确匹配:'^publish'/$ 以^开头,以$结尾) -第二个 ...
- Python 41 多表查询 和 子查询
1.查询 完整的查询语句 select [distinct] {* | 字段 | 聚合函数 | 表达式}from 表名 ...
- 制作一个 JavaScript 小游戏
简评: 作者学习了编程两个月,边学边做了一个 JavaScript 小游戏,在文中总结了自己在这个过程中的一些体会,希望能给其他初学者一些帮助. 对于很多想学编程但一直没下定决心的同学来说,最大的问题 ...
- ROS-URDF-活动关节
前言:介绍活动关节,并使机器人活动起来. 参考自:http://wiki.ros.org/urdf/Tutorials/Building%20a%20Movable%20Robot%20Model%2 ...
- 使用protobuf传递网络消息
1.获取protobuf及相关依赖 新建install_protobuf.bat脚本,粘贴以下代码 ::参考文章 https://github.com/google/protobuf/blob/mas ...
- A - Voting(queue)
Problem description There are n employees in Alternative Cake Manufacturing (ACM). They are now voti ...
- Asp.net MVC Checkbox控件 和 Nullable<bool>, 或bool?类型
@Html.CheckBoxFor() 这个方法生成两个Input HTML标签,不明白为什么这样,如果数据库是Nullable<bool>类型,就会报错. 网上的解决方法是这样: 方法一 ...
- javascript中计算点击多少次
点击事件:onclick <!DOCTYPE html> <html lang="en"> <head> <meta charset=&q ...