洛谷 - P2324 - 骑士精神 - A*搜索
生活随笔
收集整理的這篇文章主要介紹了
洛谷 - P2324 - 骑士精神 - A*搜索
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
為什么估價是16,因為最后一步復原空格可以恢復兩個位置,當然設成17、18都可以。
#include<bits/stdc++.h> using namespace std; typedef long long ll;struct State {char g[5][6]; //矩陣的狀態,0是白馬,1是黑馬,規定空格是*int hstep; //step+估價函數,至少需要的步數State() {}int h(); //估價函數h,為未歸位的騎士數void move_to(int id,int step); //嘗試移動狀態加入優先隊列bool operator==(const State& s)const {//無序mapfor(int i=0; i<5; i++)for(int j=0; j<5; j++)if(g[i][j]!=s.g[i][j])return false;return true;}bool operator<(const State& s)const {//最大堆return hstep>s.hstep;}} s_state,t_state;struct State_Hash {size_t operator()(const State&t)const {int id=0;for(int i=0; i<5; i++)for(int j=0; j<5; j++)id=(id<<1)+(t.g[i][j]-'0');return id;} };int State::h() {//估價函數,因為每次移動的是空格int res=0;for(int i=0; i<5; i++)for(int j=0; j<5; j++)if(g[i][j]!=t_state.g[i][j])res++;return res; }//vis從起點開始找到的狀態 unordered_map<State,int,State_Hash> vis; priority_queue<State> pq;int dx[]= {2,1,-1,-2,-2,-1,1,2}; int dy[]= {1,2,2,1,-1,-2,-2,-1};void State::move_to(int id,int step) {//空格向id方向移動int ox=-1;int oy=-1;for(int i=0; i<5; i++) {for(int j=0; j<5; j++) {if(g[i][j]=='*') {ox=i,oy=j;break;}}}int nx=ox+dx[id];int ny=oy+dy[id];//越界if(nx<0||ny<0||nx>4||ny>4)return;State res=*this;swap(res.g[ox][oy],res.g[nx][ny]);res.hstep=step+1+res.h();if(hstep>16)return;if(vis.count(res)) {return;} else {vis[res]=step+1;pq.push(res);} }//單向A*搜索 bool A_star() {vis.clear();while(!pq.empty())pq.pop();vis[s_state]=0;pq.push(s_state);while(!pq.empty()) {State curstate=pq.top();pq.pop();int curstep=vis[curstate];for(int i=0; i<8; i++)curstate.move_to(i,curstep);if(vis.count(t_state))return true;}return false; }int main() { #ifdef Yinkufreopen("Yinku.in","r",stdin); #endif // Yinkustrcpy(t_state.g[0],"11111");strcpy(t_state.g[1],"01111");strcpy(t_state.g[2],"00*11");strcpy(t_state.g[3],"00001");strcpy(t_state.g[4],"00000");;int T;scanf("%d",&T);while(T--) {for(int i=0; i<5; i++)scanf("%s",s_state.g[i]);if(A_star()) {int ans=vis[t_state];printf("%d\n",ans>15?-1:ans);} else {puts("-1");}}return 0; }轉載于:https://www.cnblogs.com/Yinku/p/10978329.html
創作挑戰賽新人創作獎勵來咯,堅持創作打卡瓜分現金大獎總結
以上是生活随笔為你收集整理的洛谷 - P2324 - 骑士精神 - A*搜索的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: android默认获取敏感权限
- 下一篇: 接口隔离原则——面向对象设计原则