卡片换位
你玩过华容道的游戏吗?
这是个类似的,但更简单的游戏。
看下面 3 x 2 的格子
+—+—+—+
| A | * | * |
+—+—+—+
| B | | * |
+—+—+—+
在其中放5张牌,其中A代表关羽,B代表张飞,* 代表士兵。
还有一个格子是空着的。
你可以把一张牌移动到相邻的空格中去(对角不算相邻)。
游戏的目标是:关羽和张飞交换位置,其它的牌随便在哪里都可以。
输入格式:
输入两行6个字符表示当前的局面
输出格式:
一个整数,表示最少多少步,才能把AB换位(其它牌位置随意)
例如,输入:
* A
**B
程序应该输出:
17
再例如,输入:
A B
程序应该输出:
12
资源约定:
峰值内存消耗 < 256M
CPU消耗 < 1000ms
请严格按要求输出,不要画蛇添足地打印类似:“请您输入…” 的多余内容。
所有代码放在同一个源文件中,调试通过后,拷贝提交该源码。
注意: main函数需要返回0
注意: 只使用ANSI C/ANSI C++ 标准,不要调用依赖于编译环境或操作系统的特殊函数。
注意: 所有依赖的函数必须明确地在源文件中 #include , 不能通过工程设置而省略常用头文件。
提交时,注意选择所期望的编译器类型。
#include"stdafx.h"
#include <queue>
#include <string>
#include <iostream>
#include <map>
using namespace std;
map<string, int>vis;
struct node
{
int endA;//endA为最终的A的位置,即一开始的B的位置
int endB;//endA为最终的B的位置,即一开始的A的位置
};
struct point
{
int nowx, nowy;//空格的位置
};
string input()
{
string str1, str2;
getline(cin, str1);
getline(cin, str2);
return str1 + str2;
}
int BFS(string start, node end)
{
queue<string> Q;
string Tr;
int i;
int dir[][2] = { { 1,0 },{ 0,1 },{ -1,0 },{ 0,-1 } };
point S, P;
Q.push(start);
vis[start] = 1;
while (!Q.empty())
{
Tr = Q.front();
Q.pop();
if (Tr[end.endA] == 'A'&&Tr[end.endB] == 'B') { return vis[Tr]-1; }
for (i = 0;i<6;i++)
{
if (Tr[i] == ' ')
{
S.nowx = i / 3;
S.nowy = i % 3;
}
}
for ( i = 0;i<4;i++)
{
P.nowx = S.nowx + dir[i][0];
P.nowy = S.nowy + dir[i][1];
if (P.nowx >= 0 && P.nowx<2 && P.nowy >= 0 && P.nowy<3)
{
string temp = Tr;
swap(temp[P.nowx * 3 + P.nowy], temp[S.nowx * 3 + S.nowy]);
if (vis[temp]) continue;
vis[temp] = vis[Tr] + 1;
Q.push(temp);
}
}
}
return -1;
}
int main()
{
int i, j;
string start;//每个状态的编码.
node end;
while (1)
{
start = input();
for (i = 0;i < 6;i++)
{
if (start[i] == 'A') end.endB = i;
if (start[i] == 'B') end.endA = i;
}
vis.clear();
cout << BFS(start, end) << endl;
}
return 0;
}