青蛙跳杯子(bfs)

题目描述

X星球的流行宠物是青蛙,一般有两种颜色:白色和黑色。
X星球的居民喜欢把它们放在一排茶杯里,这样可以观察它们跳来跳去。

如下图,有一排杯子,左边的一个是空着的,右边的杯子,每个里边有一只青蛙。

 

*WWWBBB


其中,W字母表示白色青蛙,B表示黑色青蛙,*表示空杯子。


X星的青蛙很有些癖好,它们只做3个动作之一:
1. 跳到相邻的空杯子里。
2. 隔着1只其它的青蛙(随便什么颜色)跳到空杯子里。
3. 隔着2只其它的青蛙(随便什么颜色)跳到空杯子里。


对于上图的局面,只要1步,就可跳成下图局面:


WWW*BBB


本题的任务就是已知初始局面,询问至少需要几步,才能跳成另一个目标局面。


输入为2行,2个串,表示初始局面和目标局面。
输出要求为一个整数,表示至少需要多少步的青蛙跳。

输入

输入为2行,2个串,表示初始局面和目标局面。

输出

输出要求为一个整数,表示至少需要多少步的青蛙跳。

样例输入

*WWBB
WWBB*

样例输出

2
#include<iostream>
#include<algorithm>
#include<queue>
#include<string>
#include<map>
using namespace std;
struct node{
	string s;
	int idx;
	int step;
};
map<string,bool> vis;
int dx[6] = {-1,1,-2,2,-3,3};
string s,tar;
void bfs(int x){
	node now,next;
	now.idx = x,now.step = 0,now.s = s;
	queue<node> q;
	q.push(now);
	vis[now.s] = 1;
	while(q.size()){
		now = q.front();
		q.pop();
		if(now.s == tar){
			cout<<now.step<<endl;
			return;
		}
		for(int i = 0;i < 6;i ++){
			next.idx = now.idx + dx[i];
			if(next.idx >= 0 && next.idx < s.length()){
				next.s = now.s,next.step = now.step + 1;
				swap(next.s[now.idx],next.s[next.idx]);
				if(!vis[next.s]){
					q.push(next);
					vis[next.s] = 1;
				}
			}
		}
	}
}
int main()
{
	cin>>s>>tar;
	int idx = s.find('*');
	bfs(idx);
	return 0;
}

 

JAVA解法:

import java.util.*;
public class Main {
	public static StringBuilder sb = new StringBuilder("");
	public static HashMap<String,Boolean> vis = new HashMap<>();
	public static String begin,end;
	public static int len;
	public static int []dx = {-1,1,-2,2,-3,3};
	public static StringBuilder swap(StringBuilder t,int p1,int p2) {
		char c = t.charAt(p1);
		t.setCharAt(p1, t.charAt(p2));
		t.setCharAt(p2, c);
		return t;
	}
	public static int bfs(int idx) {
		Queue<State> q = new LinkedList<>();
		q.add(new State(begin,idx,0));
		vis.put(begin, true);
		while(q.size() != 0) {
			State cur = q.poll();
			if(cur.s.equals(end)) {
				return cur.step;
			}
			for(int i = 0;i < 6;i ++) {
				int a = cur.idx + dx[i];
				if(a >= 0 && a < len) {
					StringBuilder t = new StringBuilder(cur.s);
					String s = swap(t,cur.idx,a).toString();
					if(!vis.containsKey(s)) {
						q.add(new State(s,a,cur.step+1));
						vis.put(s, true);
					}
				}
			}
		}
		return 1;
	}
	public static void main(String[] args) {
		Scanner sc = new Scanner(System.in);
		begin = sc.next();
		end = sc.next();
		len = begin.length();
		int idx = begin.indexOf('*');
		for(int i = 0;i < begin.length();i ++) {
			sb.append(begin.charAt(i));
		}
		System.out.println(bfs(idx));
	}
}
class State{
	String s;
	int idx;
	int step;
	State(String s,int idx,int step){
		this.s = s;
		this.idx = idx;
		this.step = step;
	}
}

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值