Poj 1077 Eight!(BFS-A*)
由结论可以知道逆序对为奇数的时候无解,f为估值函数,计算曼哈顿距离。
想用康托展开写,但多状态数码问题用数组存储状态不够,有TLE的风险,还是A*吧!
吃一个tomato宣告今日...不知道结不结束
#include<iostream> #include<cstring> #include<queue> #include<unordered_map> using namespace std; typedef pair<int,string> pii; int dir[4][2]={{-1,0},{1,0},{0,1},{0,-1}}; char op[]="lrdu"; char ch; string start,s; int f(string state){ int ans=0; for(int i=0;i<9;i++){ if(state[i]=='x') continue; int t=state[i]-'1'; ans+=abs(i%3-t%3)+abs(i/3-t/3); } return ans; } string Astar(){ string end="12345678x"; unordered_map<string,int> dist; unordered_map<string,pair<char,string> > prev; priority_queue<pii,vector<pii>,greater<pii> > heap; dist[start]=0; heap.push({f(start),start}); while(!heap.empty()){ auto t=heap.top(); heap.pop(); string state=t.second; if(state==end) break; int x,y; for(int i=0;i<9;i++){ if(state[i]=='x'){ x=i%3; y=i/3; break; } } string source=state; for(int i=0;i<4;i++){ int dx=x+dir[i][0]; int dy=y+dir[i][1]; if(dx<0 || dx>2 || dy<0 || dy>2) continue; swap(state[x+y*3],state[dx+dy*3]); if(!dist.count(state) || dist[state]>dist[source]+1){ dist[state]=dist[source]+1; prev[state]={op[i],source}; heap.push({dist[state]+f(state),state}); } state=source; } } string ans; while(end!=start){ ans=prev[end].first+ans; end=prev[end].second; } return ans; } signed main(){ ios::sync_with_stdio(false); cin.tie(0);cout.tie(0); for(int i=0;i<9;i++){ cin>>ch; start+=ch; if(ch!='x') s+=ch; } int cnt=0; for(int i=0;i<8;i++){ for(int j=i+1;j<8;j++){ if(s[i]>s[j]) cnt++; } } if(cnt&1) puts("unsolvable"); else cout<<Astar()<<endl; return 0; }
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 无需6万激活码!GitHub神秘组织3小时极速复刻Manus,手把手教你使用OpenManus搭建本
· C#/.NET/.NET Core优秀项目和框架2025年2月简报
· Manus爆火,是硬核还是营销?
· 终于写完轮子一部分:tcp代理 了,记录一下
· 【杭电多校比赛记录】2025“钉耙编程”中国大学生算法设计春季联赛(1)