搜尋(search)也是計算機常見的一種操作。常見的搜尋有深度優先搜尋(dfs)和廣度優先搜尋(bfs)。
而不管是深搜還是廣搜,實際上都隸屬於圖論中的演算法。深搜的基本思路如下:
1、訪問結點
2、對與其關聯的點進行深搜直至所有的結點均被訪問過
3、若圖中尚有結點未被訪問,則從此開始繼續深搜
深搜被發明的時候,人們常用它來尋找迷宮的解,事實上,廣搜也可以達到相同的目的。廣搜的思路如下:
1、訪問結點並將其入佇列
2、隊頭出隊,並尋找與其相關聯的結點,將其入佇列
3、若隊空則結束
從這兩個演算法的思路不難看出,深搜與廣搜的最大區別就是深搜一條道走到黑,而廣搜則一層層尋找答案。
所以我們能發現,深蒐用棧(stack)實現,廣蒐用佇列(queue)實現。
關於圖(graph)的更多演算法,將會在稍後推出。
關於模擬,其實並沒有太多好說的。就是按照題目要求用程式把某個過程展現出來。
需要注意的是,一般模擬題難度都不會很大,但**量會比較繁複,極其考驗基本功,需要大量注意細節。
今天主要講的是搜尋。搜尋的技巧有很多,包括剪枝,堆優化,雜湊表優化等等。
本日例題為
hdu - 5025
題意:孫悟空需要營救唐僧。給出n*n的網格,有且僅有乙個k和乙個t,分別代表孫悟空和唐僧的位置。
最多有m把鑰匙,最多5條蛇。走的方向只能是上下左右,每走一步需要時間為1。走到有蛇(s)的格仔
需要殺蛇,總時間消耗2(殺蛇1走路1),並且蛇殺完即消失。圖中有特殊障礙格不能走到。
問能否從k走到t並且按順序取得所有鑰匙,如果能則輸出最短的時間。
分析:本題可以算是比較基礎的bfs+狀壓題了,或者可以看做求解最短路徑。這要看我們是否使用優先佇列。
如果不使用,則是深搜;使用的話,可以看做dijkstra+heap維護。標程中使用的是優先佇列。
我們這兒開乙個三維陣列,前兩維存座標,最後一維存鑰匙狀態即當前獲得了幾把鑰匙。
由於只有五條蛇,我們使用5位二進位制數表示蛇的狀態,將會比較方便。直接設成四維陣列也是可以的。
蛇只需要殺一次,所以我們用優先佇列維護每一次搜尋花費的最小步數。
剩下的就是注意好判斷條件了。**如下:
#includeusing namespace std;
const int maxn=115;
int n,m;
int dx[4]=;
int dy[4]=;
char mp[maxn][maxn];
struct node//檢查邊界條件
int bfs()//初始化優先佇列
node cur,next;
memset(vis,false,sizeof(vis));
vis[st.x][st.y][0]=true;
q.push(st);
while(!q.empty())
else if(mp[xx][yy]=='s'){//當前位置是蛇
if(!(cur.snake&(1<
基礎演算法 模擬
剛開始有乙個空棧,我們可以對這個棧進行n次操作,每次操作之後返回棧中數字的最大值a i 如果棧為空,那麼則返回0,即a i 0。怎樣對棧進行操作題目已經給出,需要求的是 直接模擬,剛開始隊友可能想到線段樹維護最大值 需要注意的是除了題目中描述的函式的變數型別不改為long long,其他的變數型別全...
基礎演算法 模擬
給乙個長度為n的陣列a,我們現在要選出乙個序列,要求就是這個序列的中位數最接近k,輸出最長的那個滿足要求的序列在陣列a中的下標 輸入 n和k,陣列a 輸出 最長的滿足要求的序列的長度len,以及下標 p1,p2,plen 1 pi n,pi pi 1 input 5 31 2 3 4 5 outpu...
3 搜尋演算法
搜尋演算法是利用計算機的高效能來有目的的窮舉乙個問題解空間的部分或所有的可能情況,從而求出問題的解的一種方法。現階段一般有列舉演算法 深度優先搜尋 廣度優先搜尋 a 演算法 回溯演算法 蒙特卡洛樹搜尋 雜湊函式等演算法。在大規模實驗環境中,通常通過在搜尋前,根據條件降低搜尋規模 根據問題的約束條件進...