标签:
有个2*N+1的线性的棋盘,开始时最左边全是白,右边全是黑,中间一个空格。目标是黑白全部互换。求输出最少步数的操作的棋子的下标。并且要字典序最小的。
980ms险过。
不判重700ms能过。我居然多此一举的用map判重。
/* ID: modengd1 PROG: shuttle LANG: C++ */ #include <iostream> #include <stdio.h> #include <vector> #include <memory.h> #include <map> #include <string> #include <cstring> #include <queue> using namespace std; map<string,bool> vis; struct node { string sta; string ans; }; void output(string S) { for(int i=0;i<S.size();i++) { if((i%20)==0&&i>0) cout<<endl; if((i%20)==0) printf("%d",S[i]-‘0‘); else printf(" %d",S[i]-‘0‘); } cout<<endl; } int main() { freopen("shuttle.in","r",stdin); freopen("shuttle.out","w",stdout); int N; string start,target; scanf("%d",&N); for(int i=0;i<N;i++) { start.push_back(‘W‘); target.push_back(‘B‘); } start.push_back(‘ ‘); target.push_back(‘ ‘); for(int i=0;i<N;i++) { start.push_back(‘B‘); target.push_back(‘W‘); } N=2*N+1; queue<node> Q; Q.push(node{start,""}); while(!Q.empty()) { node now=Q.front();Q.pop(); if(now.sta==target) { output(now.ans); return 0; } for(int i=0;i<N;i++) { node next=now; if(now.sta[i]==‘W‘&&now.sta[i+1]==‘ ‘&&i<N-1) { next.sta[i+1]=‘W‘; next.sta[i]=‘ ‘; next.ans.push_back(i+‘1‘); if(!vis[next.sta]) Q.push(next); vis[next.sta]=true; } else if(now.sta[i]==‘W‘&&now.sta[i+1]==‘B‘&&now.sta[i+2]==‘ ‘&&i<N-2) { next.sta[i+2]=‘W‘; next.sta[i]=‘ ‘; next.ans.push_back(i+‘1‘); if(!vis[next.sta]) Q.push(next); vis[next.sta]=true; } else if(now.sta[i]==‘ ‘&&now.sta[i+1]==‘B‘&&i<N-1) { next.sta[i+1]=‘ ‘; next.sta[i]=‘B‘; next.ans.push_back(i+1+‘1‘); if(!vis[next.sta]) Q.push(next); vis[next.sta]=true; } else if(now.sta[i]==‘ ‘&&now.sta[i+1]==‘W‘&&now.sta[i+2]==‘B‘&&i<N-2) { next.sta[i+2]=‘ ‘; next.sta[i]=‘B‘; next.ans.push_back(i+2+‘1‘); if(!vis[next.sta]) Q.push(next); vis[next.sta]=true; } } } return 0; }
标签:
原文地址:http://www.cnblogs.com/modengdubai/p/4852818.html