题目

BOI 2005 Day 1
Maze
Pasvalys Language: ENG
Lithuania
7.5.2005 Page 1 of 2 MAZE
Maze (Lithuania)
Consider the following maze made of equilateral triangles:
Each vertex is described by two coordinates x and y as in the picture. Some of the edges
have a white or a black circle on them. There are two major rules that control movement
within the maze:
§ it is only allowed to pass edges with circles on them.
§ while walking through the maze it is obligatory to alternate white and black
circles; i.e. it is only allowed to pass an edge with white circle if the last circle
passed was black and vice versa. It is allowed to pass an edge with either black or
white circle on it during the first move.
TASK
Write a program to find the length of the shortest path from the entrance point to the exit
in the maze. The length of the path is defined as the number of edges (or circles) passed.
You may assume that such path always exists.
INPUT
The input file name is MAZE.IN The first line contains two integers W and H which are
the width and the height of the maze respectively (1 £ W, H £ 500). The second line
consists of four integer values: X1 Y1 X2 Y2 (0 £ X1, X2 £ W; 0 £ Y1, Y2 £ H ). (X1, Y1) are
the coordinates of the entry point in the maze and (X2, Y2) are the exit coordinates.
The next 2H+1 lines provide the description of the edges: odd lines (3rd, 5th, etc) describe
horizontal edges, and even lines (4th, 6th, etc) describe non-horizontal ones. Each line
consists of a string of characters n, w and b, where n means, that there is no circle on the
edge, and w or b means that there is white or black circle on the edge respectively. There
are no spaces between these characters. Naturally, odd lines consist of exactly W
characters, and even lines consist of exactly 2W+1 characters.
BOI 2005 Day 1
Maze
Pasvalys Language: ENG
Lithuania
7.5.2005 Page 2 of 2 MAZE
OUTPUT
Your program should output a single integer (the length of the shortest path from entrance
point to the exit in the maze) in the first (and the only) line of the file MAZE.OUT.
EXAMPLES
INPUT OUTPUT COMMENTS
2 1
0 0 2 1
bb
nwwnw
bn
6 A simple maze. One possible shortest path is
this:
(0, 0) à (1, 0) à (0, 1) à (1, 1) à (1, 0) à
(2, 0) à (2, 1)
Here is the illustration of the maze and the
shortest path:
INPUT OUTPUT COMMENTS
5 4
0 2 5 2
nnbnn
nnnwwbwnnnn
nbbbn
nnwbwwbwwnn
bwwww
nnbwbbwwbnn
nwwwn
nnnnbwbbnnn
nnwnn
22 This is the description of the maze given in the
picture on the first page. The shortest path is
this:
(0, 2) à (1, 2) à (1, 1) à (2, 1) à (2, 0) à
(3, 0) à (3, 1) à (3, 2) à (4, 1) à (3, 1) à
(3, 0) à (2, 0) à (2, 1) à (1, 1) à (1, 2) à
(1, 3) à (2, 3) à (2, 4) à (3, 4) à (3, 3) à
(4, 3) à (4, 2) à (5, 2)
(Length: 22)

分析

其实这道题就是有些变化的最短路径问题,也就是这道题对于这个“路径”有一定的要求:必须黑白交替行进。

这道题比较令人头疼的难点在于这个坐标。首先这不是正方形的格子,而是等边三角形,并且坐标表示方法也和习惯有些不同。通常我们写SPFA都会用到的是这个点的“代号”。这里用坐标就会显得比较难受。可以硬着头皮直接带着坐标写,但是我本着程序员十分钟做完的事情宁愿花一个小时来写程序解决的精神,我在读入的时候就把所有的点预处理好,以“代号”的形式来存储。从左上角,先往右,再往下,依次给每个点标号。这样做肯定有些烧脑,要理清点、边之间的关系。(读入边的颜色,所以要将边转化为点的坐标再转化为点的代号,然后进行建边)

这样一来,所有事情就像我们往常做的一样了。裸着SPFA,在其中对于边的颜色加一个小小的判断(没有颜色的边我直接就没有添加,因为肯定不会经过)。

程序

  1 #include <bits/stdc++.h>
  2 using namespace std;
  3 struct point
  4 {
  5     int x,y;
  6 }A,B;
  7 struct edge
  8 {
  9     int Next, Aim;
 10     bool Color;
 11     // TRUE: Black
 12     // FALSE: White
 13 }Edge[501*501*2];
 14 int W, H, EdgeCount, Head[501*501], start, target;
 15 int dist[501*501+1][2];
 16 char C;
 17 void Insert(int u, int v, char color)
 18 {
 19     if (color == 'w')
 20     {
 21         Edge[++EdgeCount] = (edge){Head[u], v, false};
 22         Head[u] = EdgeCount;
 23         Edge[++EdgeCount] = (edge){Head[v], u, false};
 24         Head[v] = EdgeCount;
 25     }
 26     if (color == 'b')
 27     {
 28         Edge[++EdgeCount] = (edge){Head[u], v, true};
 29         Head[u] = EdgeCount;
 30         Edge[++EdgeCount] = (edge){Head[v], u, true};
 31         Head[v] = EdgeCount;
 32     }
 33 }
 34 void SPFA()
 35 {
 36     //0: White
 37     //1: Black
 38     //freopen("maze.in","r",stdin);
 39     //freopen("maze.out","w",stdout);
 40     memset(dist, 0x3F, sizeof(dist));
 41     queue<int> Q;
 42     Q.push(start);
 43     dist[start][0] = dist[start][1] = 0;
 44     while(!Q.empty())
 45     {
 46         int u = Q.front();
 47         Q.pop();
 48         for (int i = Head[u]; i; i = Edge[i].Next)
 49         {
 50             int v = Edge[i].Aim;
 51             if (Edge[i].Color)
 52             {
 53                 if (dist[u][0]+1<dist[v][1])
 54                 {
 55                     dist[v][1] = dist[u][0]+1;
 56                     Q.push(v);
 57                 }
 58             }
 59             else
 60             {
 61                 if (dist[u][1]+1<dist[v][0])
 62                 {
 63                     dist[v][0] = dist[u][1]+1;
 64                     Q.push(v);
 65                 }
 66             }
 67         }
 68     }
 69 }
 70 /*
 71 2 1
 72 0 0 2 1
 73 bb
 74 nwwnw
 75 bn
 76 */
 77 int main()
 78 {
 79     cin >> W >> H;
 80     cin >> A.x >> A.y >> B.x >> B.y;
 81     start = A.y*(W+1)+A.x+1, target = B.y*(W+1)+B.x+1;
 82     for (int i = 1; i <= 2*H+1; i++)
 83     {
 84         if (i % 2)
 85         {
 86             for (int j = 1; j <= W; j++)
 87             {
 88                 cin >> C;
 89                 int p1 = (i-1)/2*(W+1)+j, p2 = (i-1)/2*(W+1)+j+1;
 90                 Insert(p1,p2,C);
 91             }
 92         }
 93         else
 94         {
 95             for (int j = 1; j <= 2*W+1; j++)
 96             {
 97                 cin >> C;
 98                 if (j % 2)
 99                 {
100                     int p1 = (i/2-1)*(W+1)+(j+1)/2, p2 = i/2*(W+1)+(j+1)/2;
101                     Insert(p1,p2,C);
102                 }
103                 else
104                 {
105                     int p1 = (i/2-1)*(W+1)+j/2+1, p2 = i/2*(W+1)+j/2;
106                     Insert(p1,p2,C);
107                 }
108             }
109         }
110     }
111     SPFA();
112     /*
113     for (int i = 1; i <= (W+1)*(H+1); i++)
114         cout << dist[i][0] << " " << dist[i][1] << endl;
115     */
116     cout << min(dist[target][0],dist[target][1]) << endl;
117     return 0;
118 }

转载于:https://www.cnblogs.com/OIerPrime/p/8401297.html

BOI 2005 Maze SPFA相关推荐

  1. [spfa]SSL 1535 想越狱的小杉

    Description 小杉看了看自己的纹身,明白了整个管道网是由N个小房间和若干小房间之间的单向的管道组成的. 小房间编号为不超过N的正整数. 每个管道都有一个人品限制值,小杉只能在人品不超过该限制 ...

  2. 1230: 最小花费(spfa)

    1230: 最小花费 时间限制: 1 Sec 内存限制: 128 MB 题目描述 在n个人中,某些人的银行账号之间可以互相转账.这些人之间转账的手续费各不相同.给定这些人之间转账时需要从转账金额里扣除 ...

  3. 【POJ - 3259 】Wormholes(Bellman_Ford或spfa算法,判断有向图中是否存在负环)

    题干: 农夫约翰在探索他的许多农场,发现了一些惊人的虫洞.虫洞是很奇特的,因为它是一个单向通道,可让你进入虫洞的前达到目的地!他的N(1≤N≤500)个农场被编号为1..N,之间有M(1≤M≤2500 ...

  4. 【POJ-3259】 Wormholes(判负环,spfa算法)

    题干: While exploring his many farms, Farmer John has discovered a number of amazing wormholes. A worm ...

  5. ACM算法--spfa算法--最短路算法

    求单源最短路的SPFA算法的全称是:Shortest Path Faster Algorithm.      SPFA算法是西南交通大学段凡丁于1994年发表的.     从名字我们就可以看出,这种算 ...

  6. HDU 1217 Arbitrage (Floyd + SPFA判环)

    题目链接:HDU 1217 Arbitrage 简单的货币转换问题,给定多种货币,以及货币之间的汇率,问能否通过货币的转换实现收益. 例如: 1 US Dollar buys 0.5 British ...

  7. 【HDOJ6986】Kanade Loves Maze Designing(暴力,dfs树)

    1002 Kanade Loves Maze Designing 35.26%(880/2496) 题意: 给出一棵n个点的树,每个点有权值ci,记A(i,j)表示点i和j之间路径上的不同权值个数,求 ...

  8. BZOJ.4500.矩阵(差分约束 SPFA判负环 / 带权并查集)

    BZOJ 差分约束: 我是谁,差分约束是啥,这是哪 太真实了= = 插个广告:这里有差分约束详(并不)解. 记\(r_i\)为第\(i\)行整体加了多少的权值,\(c_i\)为第\(i\)列整体加了多 ...

  9. NOI 2005 聪聪可可

    1784 聪聪与可可 2005年NOI全国竞赛 时间限制: 1 s 空间限制: 128000 KB 题目等级 : 大师 Master 题解 题目描述 Description 在一个魔法森林里,住着一只 ...

最新文章

  1. 苹果Q1财报出炉:手机收入下滑15%,服务收入增长19%
  2. 指尖检测的几种新方法
  3. SVM+HOG:用初次训练的.xml分类器在负样本原图上检测生成HardExample样本
  4. hihocoder1398 网络流五之最大权闭合子图
  5. linux 查看历史打印,2019-02-01 Linux查看用户/历史命令
  6. java 多线程变量可见性_Java多线程:易变变量,事前关联和内存一致性
  7. java jdbc 乱码_【求助】为什么用纯java jdbc插入mysql一直乱码
  8. 专题导读:大数据整理
  9. IMU传感器和预积分
  10. 洛谷 P1396 营救
  11. EDA技术与应用实验二(PowerShell实现)
  12. vue脚手架下载及使用
  13. 全排列(从大到小排列)
  14. Wordpress网页直接插入bilibili视频方法
  15. 【MATLAB】求解约束条件下的目标函数最值(fmincon用法解析)
  16. js面向对象prototype
  17. vue移动端项目经验
  18. 聊聊机器人学习中的“投资”与“消费”(节选)
  19. cad打印黑白图纸,该如何打印呢?
  20. 华为OD机试 - 硬件产品销售方案(Java JS Python)

热门文章

  1. android租车管理系统,毕业设计(论文)-基于Android的学校租车管理系统的设计与开发.doc...
  2. es不建议模糊搜索_elasticsearch match模糊查询
  3. Unity Shader 素描渲染
  4. 手机照片局部放大镜_手机里竟然自带quot;放大镜quot;,很远也感觉近在眼前,真的涨知识了...
  5. 浙江大学计算机考研资料汇总
  6. pypi打包非代码文件
  7. Thinkphp 6 + Vue 2 + ElementUI + Vxe-table 前后端分离的,一键生成代码和API接口的,通用后台管理系统 快速开发框架,开发小程序和APP的推荐框架!
  8. 全球地名中英文对照表(C)
  9. 在 PowerShell 中使用 SQL Server (1)
  10. 陶瓷天线AN1603-433