計蒜客題解 T1213 拯救行動

2021-10-03 12:31:09 字數 3318 閱讀 1202

計蒜客 oj,

公主被惡人抓走,被關押在牢房的某個地方。牢房用 n×m(n,m≤200) 的矩陣來表示。矩陣中的每項可以代表道路(@)、牆壁(#)、和守衛(x)。

英勇的騎士(r)決定孤身一人去拯救公主(a)。我們假設拯救成功的表示是 "騎士到達了公主所在的位置"。由於在通往公主所在位置的道路中可能遇到守衛,騎士一旦遇到守衛,必須殺死守衛才能繼續前進。

現假設騎士可以向上、下、左、右四個方向移動,每移動乙個位置需要 1 個單位時間,殺死乙個守衛需要花費額外的 1 個單位時間。同時假設騎士足夠強壯,有能力殺死所有的守衛。

給定牢房矩陣,公主、騎士和守衛在矩陣中的位置,請你計算拯救行動成功需要花費最短時間。

1、兩個整數代表 n 和 m,(n,m≤200).

2、隨後 n 行,每行有 m 個字元。"@" 代表道路,"a" 代表公主,"r" 代表騎士,"x" 代表守衛, "#" 代表牆壁。

如果拯救行動成功,輸出乙個整數,表示行動的最短時間。

如果不可能成功,輸出 "impossible"。

7 8

#@#####@

#@a#@@r@

#@@#x@@@

@@#@@#@#

#@@@##@@

@#@@@@@@

@@@@@@@@

13
13 40

@x@@##x@#x@x#***x##@#x@x@@#x#@#x#@@x@#@x

xx###x@x#@@##xx@@@#@x@@#x@***@@#x@#x@@x@

#@x#@x#x#@@##@@x#@xx#***@@x##@@@#@x@@x@x

@##x@@@x#xx#@@#***x#@@x@x@#@x@@@x@#@#x@#

@#***xx##@@x##x@***@@#x@x####@@@x#x##@#@

#***#@#x##***x@@#xx@@@x@***#@#***@x#####

#x@***x#@x@@@@##@x#xx#***@#xx#@#####x#@x

xx##@#@x##x##x#@x#@a#xx@##@#@##xx@#@@x@x

x#x#@x@#x#@##@xrx@x#***x@##x##xx#@#x@xx@

#x@@#@###x##x@x#@@#@@x@x@@xx@@@@##@@x@@x

x#xx@x###@***#@#x#@@###@#@##@x#@x@#@@#@@

#@#x@x#x#x###@x@@***####x@x##@x####xx#@x

#x#@x#x######@@#x@#***x#xx@@@#xx#x#####@

7
乙個 n*m 大小的迷宮,我們從 r 位置出發(也就是起點),字元 @ 表示可以安全通行的方格,字元 # 表示牆壁(也就是不能走),字元 x 代表守衛(守衛可以殺死,但是必須付出額外的 1 個單位時間),字元 a 表示仙藥(也就是終點)。要求輸出從 @ 到 a 的最短路徑。那麼迷宮問題的基本要素全齊了,所以本題就是一道 bfs 模板題。

本題和以前的 bfs 模板題唯一的不同就是所有守衛可以殺死,但是需要付出額外的時間。因此意味著 x 的地方是可以走的,只是要多付出 1 個單位時間。也就是說,走 x 地方,需要 2 個時間單位;走 @ 地方,需要 1 個時間單位。

省略。如果想看類似的資料分析,可以看以前的文章,主要是我偷懶了,畫圖太累了,請原諒。

1、讀入資料,並寫入到合適的資料結構中。

2、找到起點位置,將起點加入到佇列 q 中。

3、記錄終點位置資訊。

4、開始 bfs 遍歷。直到找到終點或者遍歷所有節點而無法到達終點。注意:走 x 地方,需要 2 個時間單位;走 @ 地方,需要 1 個時間單位。

#include #include //位置定義

struct pos ;

const int maxn = 202;

struct maze ;

int bfs(maze &maze);

int main() ;//迷宮定義並將所有初始化為零

//讀入迷宮長寬

scanf("%d %d", &maze.row, &maze.col);

//讀入迷宮資料

int i,j;

for (i=0; i0) else

return 0;

}int bfs(maze &maze) , , , };//騎士的移動方法

pos cur;//當前位置

pos next;//下乙個位置

//加入起點

cur.x = maze.x1;

cur.y = maze.y1;

cur.cost = 0;

maze.visit[cur.x][cur.y] = true;//設定本節點已經訪問

q.push(cur);

//開始遍歷

while (!q.empty()) else

//判斷通過性

if (next.x>=0&&next.x=0&&next.y1、如何表示乙個節點的座標,以及該節點到起點的距離。這裡我用乙個自定義的結構體來表示。如下所示:

struct pos ;

2、如何表示乙個迷宮。這裡我將所有迷宮資訊全部放在乙個自定義結構體中,增強了**可讀性。如下所示:

const int maxn = 200;

struct maze ;

3、如何表示所有移動可能性。如下所示:

const pos move = , , , };//定義移動方法
4、新節點通過性判斷問題。根據題目進行判斷,基本包括以下幾個方面:

(1)這個位置可以走,如本題中用字元 . 表示。如下所示:

maze.data[next.x][next.y]!='#'
注意,只要不是 # 就認為這個節點是可以走的。至於是否是守衛,我們等彈出的時候再判斷。這個細節是和標準走迷宮不一樣的。

(2)這個位置沒有訪問過。如下所示:

maze.visit[next.x][next.y]==false
(3)這個位置處於迷宮內。這個判斷和您程式對迷宮定義有關。如下所示:

next.x>=0&&next.x=0&&next.y(4)判斷這個位置是不是守衛。在彈出隊首元素的時候才判斷。如下所示:

if (maze.data[cur.x][cur.y]=='x')

當然,也可以在走到本位置的時候進行判斷。不管在**判斷,是不會影響結果的,這是由於 bfs 的特性決定的。

計蒜客 T 1213 拯救行動 bfs 優先佇列)

拯救行動 題目描述 現假設騎士可以向上 下 左 右四個方向移動,每移動乙個位置需要 1 個單位時間,殺死乙個守衛需要花費額外的 1 個單位時間。同時假設騎士足夠強壯,有能力殺死所有的守衛。給定牢房矩陣,公主 騎士和守衛在矩陣中的位置,請你計算拯救行動成功需要花費最短時間。輸入格式 1 兩個整數代表 ...

計蒜客題解 T1244 單詞序列

計蒜客 oj,我的 oj,蒜頭君給出兩個單詞 開始單詞和結束單詞 以及乙個詞典。找出從開始單詞轉換到結束單詞,所需要的最短轉換序列。轉換的規則如下 1 每次只能改變乙個字母 2 轉換過程 現的單詞 除開始單詞和結束單詞 必須存在於詞典中 例如 開始單詞為 hit,結束單詞為 cog,詞典為 hot,...

計蒜客 矩陣翻轉 題解

time 1000ms memory 65536k desc 曉萌最近在做乙個翻轉的應用,你可能也知道,其實是由乙個個的點組成的。於是,曉萌想先做乙個可以翻轉矩陣的程式,來解決他問題的核心部分。input fomat 輸入第一行包括由空格分開的整數 m,n,t 0 n,m 200 t 的值為 0 或...