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. PosixIO

    1.打开文件 int open(const char *pathname, int flags); int open(const char *pathname, int flags, mode_t m ...

  2. 如何选择面向移动设备的html5开发框架

    很久以前整理了篇将手机网站做成手机应用的JS框架.时隔一年多,很多新的技术已经出现,下面再来总结下还有哪些框架是适合面向手机设备的开发的. 1.jQuery Mobile jQuery Mobile ...

  3. Struts1、WebWork、Struts2介绍

    一.Struts1 1.Struts1原理简介 Struts1框架以ActionServlet作为控制器核心,整个应用由客户端请求驱动.当客户端向Web应用发送请求时,请求被Struts1的核心控制器 ...

  4. 第五组UI组件:ProgressBar及其子类

    ProgressBar组件也是一组重要的组件,ProgressBar本身代表了进度条组件,它还派生了两个常用的组件:SeekBar和RatingBar.ProgressBar及其子类在用上十分相似,只 ...

  5. SuperSocket入门(五)-常用协议实现模版及FixedSizeReceiveFilter示例

             Socket里面的协议解析是Socket通讯程序设计中最复杂的地方,如果你的应用层协议设计或实现不佳,Socket通讯中常见的粘包,分包就难以避免.SuperSocket内置了命令行 ...

  6. iOS开发中@property的属性weak nonatomic strong readonly等介绍

    @property与@synthesize是成对出现的,可以自动生成某个类成员变量的存取方法.在Xcode4.5以及以后的版本,@synthesize可以省略. 1.atomic与nonatomica ...

  7. Swiper --移动端触摸滑动插件

    Swiper使用方法 1.首先加载插件,需要用到的文件有swiper.min.js和swiper.min.css文件. <!DOCTYPE html> <html> <h ...

  8. 分布式搜索之搭建Solrcloud(Solr集群)

    Solrcloud介绍: SolrCloud(solr集群)是Solr提供的分布式搜索方案. 当你需要大规模,容错,分布式索引和检索能力时使用SolrCloud. 当索引量很大,搜索请求并发很高时,同 ...

  9. 如何编写一个gulp插件

    很久以前,我们在"细说gulp"随笔中,以压缩JavaScript为例,详细地讲解了如何利用gulp来完成前端自动化. 再来短暂回顾下,当时除了借助gulp之外,我们还利用了第三方 ...

  10. java系列笔记---正则表达式(2)

    正则表达式 说真的正则表达式真不好写,当我收集资料准备开始写的时候,发现收集的东西越来越多范围也越来越广,我文章的前提就是文章要清晰, 在缕清自己思路之后,我从先简后难的方式来写有关正表达式,你们如果 ...