hdu-1010 dfs+剪枝
思路:
剪枝的思路参考博客:http://www.cnblogs.com/zibuyu/archive/2012/08/17/2644396.html 在其基础之上有所改进
题意可以给抽象成给出一个图,让你求S点到D点之间是否存在一条长度为T的道路。求两地之间的距离用的是dfs,而dfs在这里的关键是找到回溯的条件,就是当到达D点并且剩余步数为0时,则符合题意的要求,由于我们只需要知道这样一条长度为T的路径是否存在,因此当我们发现存在的时候,只需要将一个全局flag给设置为1即可,然后从此之后的所有dfs调用都直接return。
另外关键的问题就是剪枝。当我们的思路走到求两个点的距离时,我们应当“俯视”一下——这两个点S和D,他们之间的距离从整个图上来看有什么性质。在这里有这样的规律:aaarticlea/png;base64,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" alt="" />
也就是一开始给我们的两个起始点S和D,如果他们之间距离的最小值的奇偶性和T的奇偶性是不同的,那么在一开始我们就可以判断——“NO”!因为0->0和1->1无论怎么走需要的步数都为偶数步,1->0或0->1无论怎么走需要的步数都为奇数步。利用这点,从一开始我们就可以进行奇偶剪枝。
还有一个并不影响最后AC但是也值得思考的一个剪枝,就是在一开始的时候给定图可走的点数就小于T,那就直接不需要考虑。
代码:
#include <iostream>
#include <cstring>
#include <cstdio>
#include <cmath>
using namespace std; char G[][];//G[n][m]
int dx,dy;
int n,m,t;
int dir[][] = {{,-},{,},{,},{-,}};
int flag; void dfs(int cx,int cy,int step) {
//now we're at (cx,cy),there're "step" steps left to get to (dx,dy)
if(cx<||cx>n||cy<||cy>m)
return;
if(flag) return;
if(cx==dx&&cy==dy&&step==) {
flag = ;
return ;
}
for(int i = ;i < ;i++) {
int nx = cx+dir[i][];
int ny = cy+dir[i][];
if(nx<||ny<||nx>n||ny>m) continue;//(1)over-border
if(G[nx][ny] == 'X') continue;//(2)can't get to(nx,ny)
G[cx][cy] = 'X';
dfs(nx,ny,step-);
if(flag) return;
G[cx][cy] = '.';
}
} int main()
{
int sx,sy;
int i,j;
while(scanf("%d%d%d",&n,&m,&t)&&(n!=||m!=||t!=)) {
int wall = ;
for(i=;i<=n;++i)
{
scanf("%s",G[i]+);
for(j=;j<=m;++j)
{
if(G[i][j]=='S')
{
sx=i;
sy=j;
}
if(G[i][j]=='D')
{
dx=i;
dy=j;
}
if(G[i][j]=='X') wall++;
}
}
//cut branches-1
if((abs(sx-dx)+abs(sy-dy))% != t%) {
cout<<"NO"<<endl;
continue;
}
//cut branches-2
if(n*m-wall < t) {
cout<<"NO"<<endl;
continue;
}
flag = ;
dfs(sx,sy,t);
if(flag) cout<<"YES"<<endl;
else cout<<"NO"<<endl;
}
return ;
}
hdu-1010 dfs+剪枝的更多相关文章
- Tempter of the Bone HDU 1010(DFS+剪枝)
Problem Description The doggie found a bone in an ancient maze, which fascinated him a lot. However, ...
- poj 1564 Sum It Up | zoj 1711 | hdu 1548 (dfs + 剪枝 or 判重)
Sum It Up Time Limit : 2000/1000ms (Java/Other) Memory Limit : 65536/32768K (Java/Other) Total Sub ...
- hdu 4109 dfs+剪枝优化
求最久时间即在无环有向图里求最远路径 dfs+剪枝优化 从0节点(自己添加的)出发,0到1~n个节点之间的距离为1.mt[i]表示从0点到第i个节点眼下所得的最长路径 #include<iost ...
- HDU 1010 (DFS搜索+奇偶剪枝)
题目链接: http://acm.hdu.edu.cn/showproblem.php?pid=1010 题目大意:给定起点和终点,问刚好在t步时能否到达终点. 解题思路: 4个剪枝. ①dep&g ...
- hdu 1010(DFS) 骨头的诱惑
http://acm.hdu.edu.cn/showproblem.php?pid=1010 题目大意从S出发,问能否在时间t的时候到达终点D,X为障碍 需要注意的是要恰好在t时刻到达,而不是在t时间 ...
- HDU 5113 dfs剪枝
题意:告诉格子规格,颜色个数,以及每个颜色能涂得格子数目,问是否能够实现相邻两个格子的颜色数目不相同. 分析:因为数据很小,格子最多是5 * 5大小的,因此可以dfs.TLE了一次之后开始剪枝,31m ...
- hdu 1010 dfs搜索
Tempter of the Bone Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Othe ...
- hdu 1518 dfs+剪枝
题目大意:几根棒子能否组成一个正方形 Sample Input3 //测试组数4 1 1 1 1 //棒子数目以及每根棒子的长度5 10 20 30 40 508 1 7 2 ...
- hdu 1010:Tempter of the Bone(DFS + 奇偶剪枝)
Tempter of the Bone Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Othe ...
- HDU 1010 Tempter of the Bone --- DFS
HDU 1010 题目大意:给定你起点S,和终点D,X为墙不可走,问你是否能在 T 时刻恰好到达终点D. 参考: 奇偶剪枝 奇偶剪枝简单解释: 在一个只能往X.Y方向走的方格上,从起点到终点的最短步数 ...
随机推荐
- 线程、委托、lambda运算符的简单示例
using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.T ...
- 零基础学习云计算及大数据DBA集群架构师【企业级运维技术及实践项目2015年1月29日周五】
LNMP/LEMP项目搭建 { 项目框架 # Linux_____WEB_____PHP_____DB # rhel7_____apache__-(libphp5.so)-__php__-(php-m ...
- C# Wpf集合双向绑定
说明: msdn中 ObservableCollection<T> 类 表示一个动态数据集合,在添加项.移除项或刷新整个列表时,此集合将提供通知. 在许多情况下,所使用的数据是对 ...
- get the text value of a selected option.
<select id="myselect"> <option value="1">Mr</option> <optio ...
- Android客户端采用Http 协议Post方式请求与服务端进行数据交互(转)
http://blog.csdn.net/javanian/article/details/8194265
- C++ 数组作为函数参数时,传递数组大小的方法
废话不多说,先上错误示范: void fun(int arr[arr_num]) { // ... } int main() { // ... int *arr = new int[10]; fun( ...
- uva 1378 A Funny Stone Game (博弈-SG)
题目链接:http://vjudge.net/problem/viewProblem.action?id=41555 把第i堆的每个石子看出一堆个数为n-i的石子,转换为组合游戏 #include & ...
- 【USACO 1.2.3】命名那个数字
[问题描述] 在威斯康辛州牛大农场经营者之中,都习惯于请会计部门用连续数字给母牛打上烙印.但是,母牛用手机时并没感到这个系统的便利,它们更喜欢用它们喜欢的名字来呼叫它们的同伴,而不是用像这个的语句&q ...
- Yii2的相关学习记录,后台模板和gii(三)
前面已经可以正常登录,但我们需要体验下最常用的增删查改的操作.这里就需要gii,通过gii可以方便的生成表单.表格的框架,不需要我们再写重复的东西. gii访问地址:http://localhost/ ...
- php设计模式之简单工厂模式
①抽象基类:类中定义抽象一些方法,用以在子类中实现 ②继承自抽象基类的子类:实现基类中的抽象方法 ③工厂类:用以实例化所有相对应的子类 /** * * 定义个抽象的类,让子类去继承实现它 * */ a ...