A计划

Time Limit: 3000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)
Total Submission(s): 15567    Accepted Submission(s): 3886

Problem Description


怜的公主在一次次被魔王掳走一次次被骑士们救回来之后,而今,不幸的她再一次面临生命的考验。魔王已经发出消息说将在T时刻吃掉公主,因为他听信谣言说吃
公主的肉也能长生不老。年迈的国王正是心急如焚,告招天下勇士来拯救公主。不过公主早已习以为常,她深信智勇的骑士LJ肯定能将她救出。
现据密探
所报,公主被关在一个两层的迷宫里,迷宫的入口是S(0,0,0),公主的位置用P表示,时空传输机用#表示,墙用*表示,平地用.表示。骑士们一进入时
空传输机就会被转到另一层的相对位置,但如果被转到的位置是墙的话,那骑士们就会被撞死。骑士们在一层中只能前后左右移动,每移动一格花1时刻。层间的移
动只能通过时空传输机,且不需要任何时间。
 

Input

输入的第一行C表示共有C个测试数据,每个测试数据的前一行有三个整数N,M,T。 N,M迷宫的大小N*M(1 <= N,M <=10)。T如上所意。接下去的前N*M表示迷宫的第一层的布置情况,后N*M表示迷宫第二层的布置情况。
 

Output

如果骑士们能够在T时刻能找到公主就输出“YES”,否则输出“NO”。
 

Sample Input

1
5 5 14
S*#*.
.#...
.....
****.
...#.

 
..*.P
#.*..
***..
...*.
*.#..
 

Sample Output

YES
 
Source
 
 
题目的意思很清楚了,很明显的搜索题,根据题意枚举一下情况就好。本以为很容易过的题,没想到因为一个三维数组而一直TLE!!!!!所以这题目让我感受到了N维数组在效率上的影响是有多大!!!
 
先上AC代码。
import java.util.Scanner;

public class Main {

    public static boolean flag = false;

    public static char[][] mg1;

    public static char[][] mg2;

    public static void main( String[] args ) {
int n, m, t;
int q;
Scanner sc = new Scanner( System.in );
while( sc.hasNext() ) {
q = sc.nextInt();
for( int c = 0; c < q; c++ ) {
n = sc.nextInt();
m = sc.nextInt();
t = sc.nextInt();
flag = false;
mg1 = new char[ n ][ m ];
mg2 = new char[ n ][ m ];
for( int ni = 0; ni < n; ni++ ) {
mg1[ ni ] = sc.next().toCharArray();
}
for( int ni = 0; ni < n; ni++ ) {
mg2[ ni ] = sc.next().toCharArray();
}
search( mg1, new Point2D( 0, 0 ), t );
if( flag ) {
System.out.println( "YES" );
} else {
System.out.println( "NO" );
}
}
}
} /*
* search和seach2 分别是两层迷宫的搜索,逻辑上基本是相同的,注意一下当传送之后的情况,如果是#和*都是死路就行了。
*/
private static void search( char[][] mg1, Point2D point, int t ) {
if( !constraint( point, mg1, t ) )
return;
if( mg1[ point.n ][ point.m ] == '*' )
return;
if( mg1[ point.n ][ point.m ] == 'P' ) {
flag = true;
}
if( mg1[ point.n ][ point.m ] == '#' ) {
if( mg2[ point.n ][ point.m ] == '#' || mg2[ point.n ][ point.m ] == '*' ) {
return;
}
search2( mg2, new Point2D( point.n, point.m ), t );
} else {
//设置为*,防止重复搜索,效果类似于visited标记数组。
mg1[ point.n ][ point.m ] = '*';
search( mg1, new Point2D( point.n, point.m + 1 ), t - 1 );
search( mg1, new Point2D( point.n, point.m - 1 ), t - 1 );
search( mg1, new Point2D( point.n + 1, point.m ), t - 1 );
search( mg1, new Point2D( point.n - 1, point.m ), t - 1 );
mg1[ point.n ][ point.m ] = '.';
}
} private static void search2( char[][] mg2, Point2D point, int t ) {
if( !constraint( point, mg2, t ) )
return;
if( mg2[ point.n ][ point.m ] == '*' )
return;
if( mg2[ point.n ][ point.m ] == 'P' ) {
flag = true;
}
if( mg2[ point.n ][ point.m ] == '#' ) {
if( mg1[ point.n ][ point.m ] == '#' || mg1[ point.n ][ point.m ] == '*' ) {
return;
}
search( mg1, new Point2D( point.n, point.m ), t );
} else {
mg2[ point.n ][ point.m ] = '*';
search2( mg2, new Point2D( point.n, point.m + 1 ), t - 1 );
search2( mg2, new Point2D( point.n, point.m - 1 ), t - 1 );
search2( mg2, new Point2D( point.n + 1, point.m ), t - 1 );
search2( mg2, new Point2D( point.n - 1, point.m ), t - 1 );
mg2[ point.n ][ point.m ] = '.';
}
} private static boolean constraint( Point2D point, char[][] mg, int t ) {
if( point.n < 0 || point.n >= mg.length || point.m < 0 || point.m >= mg[ 0 ].length ) {
return false;
}
if( t < 0 ) {
return false;
}
return true;
} } class Point2D { public int n; public int m; public Point2D( int n, int m ) {
this.n = n;
this.m = m;
} }

我原本的写法不是这样的,我原本的思路是使用三维数组mg[x][y][z]去直观的表示,如果发生跳跃就直接 (x+1)%2就可以简化了代码量了。

However,too young too naive~三维数组的效率相比二维数组真的慢好多好多,以后需要谨记,谨慎使用多维数组!

一下就是TLE的三维数组的代码

(超时代码)

import java.util.Scanner;

public class Main {

    public static boolean flag = false;

    public static void main( String[] args ) {
int n, m, t;
int q;
Scanner sc = new Scanner( System.in );
while( sc.hasNext() ) {
q = sc.nextInt();
for( int c = 0; c < q; c++ ) {
n = sc.nextInt();
m = sc.nextInt();
t = sc.nextInt();
flag = false;
char[][][] mg = new char[ 2 ][ n ][ m ];
for( int i = 0; i < 2; i++ ) {
for( int ni = 0; ni < n; ni++ ) {
String s = sc.next();
mg[i][ni] = s.toCharArray();
}
}
search( mg, new Point( 0, 0, 0 ), t );
if( flag ) {
System.out.println( "YES" );
} else {
System.out.println( "NO" );
}
}
}
} private static void search( char[][][] mg, Point point, int t ) {
if( !constraint( point, mg, t ) )
return;
if( mg[ point.c ][ point.n ][ point.m ] == '*' )
return;
if( mg[ point.c ][ point.n ][ point.m ] == 'P' ) {
flag = true;
}
if( mg[ point.c ][ point.n ][ point.m ] == '#' ) {
if( mg[ ( point.c + 1 ) % 2 ][ point.n ][ point.m ] == '#' || mg[ ( point.c + 1 ) % 2 ][ point.n ][ point.m ] == '*' ) {
return;
}
search( mg, new Point( ( point.c + 1 ) % 2, point.n, point.m ), t );
} else {
mg[ point.c ][ point.n ][ point.m ] = '*';
search( mg, new Point( point.c, point.n, point.m + 1 ), t - 1 );
search( mg, new Point( point.c, point.n, point.m - 1 ), t - 1 );
search( mg, new Point( point.c, point.n + 1, point.m ), t - 1 );
search( mg, new Point( point.c, point.n - 1, point.m ), t - 1 );
mg[ point.c ][ point.n ][ point.m ] = '.';
}
} private static boolean constraint( Point point, char[][][] mg, int t ) {
if( point.n < 0 || point.n >= mg[ 0 ].length || point.m < 0 || point.m >= mg[ 0 ][ 0 ].length ) {
return false;
}
if( t < 0 ){
return false;
}
return true;
} } class Point { public int c; public int n; public int m; public Point( int c, int n, int m ) {
this.c = c;
this.n = n;
this.m = m;
} }
Orz~~~~~~~
 

[HDU 2102] A计划(搜索题,典型dfs or bfs)的更多相关文章

  1. 搜索分析(DFS、BFS、递归、记忆化搜索)

    搜索分析(DFS.BFS.递归.记忆化搜索) 1.线性查找 在数组a[]={0,1,2,3,4,5,6,7,8,9,10}中查找1这个元素. (1)普通搜索方法,一个循环从0到10搜索,这里略. (2 ...

  2. HDU 2102 A计划(BFS/DFS走迷宫)

    A计划 Time Limit: 3000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) Total Submis ...

  3. hdu 2102 A计划

    题目连接 http://acm.hdu.edu.cn/showproblem.php?pid=2102 A计划 Description 可怜的公主在一次次被魔王掳走一次次被骑士们救回来之后,而今,不幸 ...

  4. HDU 2102 A计划(两层地图加时间限制加传送门的bfs)

    传送门: http://acm.hdu.edu.cn/showproblem.php?pid=2102 A计划 Time Limit: 3000/1000 MS (Java/Others)    Me ...

  5. HDU 2102 A计划 DFS与BFS两种写法 [搜索]

    1.题意:一位公主被困在迷宫里,一位勇士前去营救,迷宫为两层,规模为N*M,迷宫入口为(0,0,0),公主的位置用'P'标记:迷宫内,'.'表示空地,'*'表示墙,特殊的,'#'表示时空传输机,走到这 ...

  6. hdu 2102 A计划(优先队列+dfs)

    改了好久,上午来实验室打出来了,运行就是不对,一直找啊找!还是没找到,最后突然停电了,打好的代码还没保存呢! 刚才来的时候又重新打了一遍!!!结果一个小小的错误wrong了好久!!! 在dfs值返回时 ...

  7. HDU 2102 A计划 (BFS或DFS)

    题意:中文题. 析:是一个简单的搜索,BFS 和 DFS都可行, 主要是这个题有一个坑点,那就是如果有一层是#,另一个层是#或者*,都是过不去的,就可以直接跳过, 剩下的就是一个简单的搜索,只不过是两 ...

  8. HDU 2102 A计划(DFS)

    题目链接 Problem Description 可怜的公主在一次次被魔王掳走一次次被骑士们救回来之后,而今,不幸的她再一次面临生命的考验.魔王已经发出消息说将在T时刻吃掉公主,因为他听信谣言说吃公主 ...

  9. hdu 2102 a计划问题。。 双层dfs问题

    Problem Description 可怜的公主在一次次被魔王掳走一次次被骑士们救回来之后,而今,不幸的她再一次面临生命的考验.魔王已经发出消息说将在T时刻吃掉公主,因为他听信谣言说吃公主的肉也能长 ...

随机推荐

  1. JS前端的分享功能

    给网页加上分享代码,借助网友的力量推广网站,目前已经很流行了 以下是网页代码 QQ空间分享代码如下: <a href="javascript:void(0);" onclic ...

  2. php知识点总结(一)

    1.把数组以表格的形式显示 <?php $array = array( '书籍' =>  array( '生活',  '人与自然','动物世界'), '体育用品' =>  array ...

  3. 各个浏览器开启CSS Grid Layout的方式

    2017年3月,Chrome.Firefox将开启默认支持. 当然对于很多人等不及浏览器默认支持,想提前体验一把,这里提供一些打开方式: 1.Chrome 在浏览器中输入:chrome://flags ...

  4. SuperSocket入门(二)- 探索AppServer、AppSession,Conmmand和App.config

          在上一篇文章中,我们已经了解到了如何在SuperSocket处理客户端请求. 同时我们可能会发现一个问题,如果我们的服务器端包含有很多复杂的业务逻辑,这样的switch/case代码将会很 ...

  5. Dubbo源码学习--集群负载均衡算法的实现

    相关文章: Dubbo源码学习文章目录 前言 Dubbo 的定位是分布式服务框架,为了避免单点压力过大,服务的提供者通常部署多台,如何从服务提供者集群中选取一个进行调用, 就依赖Dubbo的负载均衡策 ...

  6. C#中let字句

    应用场景: 在查询表达式中,存储子表达式的结果有时很有用,这样可以在随后的子句中使用. 可以使用 let 关键字完成这一工作,该关键字可以创建一个新的范围变量,并且用您提供的表达式的结果初始化该变量. ...

  7. datagridview数据绑定操作数据库实现增删改查

    DataSet数据集,数据缓存在客户端内存中,支持断开式连接.DataGridView控件绑定DataSet时,它自动的改变的DS的行的状态,而且在做增删改查的时候,可以借助SqlCommandBui ...

  8. cmake的两个命令: option 和 configure_file

    本节要讨论的是cmake的两个命令: option 和 configure_file option 选项,让你可以根据选项值进行条件编译. configure_file 配置文件,让你可以在代码文件中 ...

  9. mysql 打开sql日志,记录所有sql

    我使用的mysql版本为:5.7.11 win7环境 记录下下载地址,省得每次百度搜了:http://dev.mysql.com/downloads/installer/ mysql 默认没有开启sq ...

  10. Java 文件句柄泄露问题解决小记

    维护 WebIDE 免不了要管理很多的文件, 自从我们线上系统增加了资源回收功能,便一直受一个问题困扰:后台线程解绑目录时偶尔报错,看症状因为是某些文件被占用了,目录不能解绑.但是由于系统中很多地方都 ...