B - Pour Water(Week2 作业)

题目叙述:

倒水问题
“fill A” 表示倒满A杯,"empty A"表示倒空A杯,“pour A B” 表示把A的水倒到B杯并且把B杯倒满或A倒空。
Input
输入包含多组数据。每组数据输入 A, B, C
数据范围 0 < A <= B 、C <= B <=1000 、A和B互质。
Output
你的程序的输出将由一系列的指令组成。这些输出行将导致任何一个罐子正好包含C单位的水。每组数据的最后一行输出应该是“success”。输出行从第1列开始,不应该有空行或任何尾随空格。
Sample Input
2 7 5
2 7 4
Sample Output
fill B
pour B A
success
fill A
pour A B
fill A
pour A B
success

题目思路:

对当前杯子A,B的操作可以分为六种情况:
1、把A中的水倒空
2、把B中的水倒空
3、(A中不满)将A倒满水
4、(A中不满)将B中的水倒入A中(A是否倒满?)
5、(B中不满)将B中倒满水
6、(B中不满)将A中的水倒入B中(B是否倒满?)
利用bfs搜索,从(0,0)开始,直到其中一个杯子中水的体积等于C时停止。根据上述条件,将两个杯子可能的下一状态放入队列中,并利用map记录父节点与子节点,同时利用flag记录得到此时状态的条件,方便后续输出具体操作。
最后输出,利用递归实现具体操作的输出。

代码实现:

#include<iostream>
#include<queue>
#include<map> 
using namespace std;
struct node
{
	int x,y;
	int flag;
	bool operator<(const node &s) const 
	{
		return x!=s.x ? x<s.x:y<s.y;
	}
};
map<node, node> record;
queue<node> s;
void print(node p)
{
	if(p.flag==1)
		cout<<"empty A"<<endl;
	else if(p.flag==2)
		cout<<"empty B"<<endl;
	else if(p.flag==3)
		cout<<"fill A"<<endl;
	else if(p.flag==4)
		cout<<"pour B A"<<endl;
	else if(p.flag==5)
		cout<<"fill B"<<endl;
	else if(p.flag==6)
		cout<<"pour A B"<<endl;
}
void judge(node now,node nex)
{
    if (record.find(nex) == record.end()) 
    { 
        record[nex]=now;
        s.push(nex);
    }
}
void printff(node p)
{
	if((p.x==0&&p.y==0)||(record.find(p)==record.end())) 
	{
		print(p);
		return;
	}
	printff(record[p]);
	print(p);	
}
void bfs(int A,int B,int C)
{
	node z;
	z.x=0;
	z.y=0;
	z.flag=0;
	s.push(z);
	while(!s.empty())
	{
		node now=s.front();
		s.pop();
		node nex;
		if(now.x==C||now.y==C)
		{
			printff(now);
			return;
		}
		if(now.x>0)
		{
			nex.x=0;
			nex.y=now.y;
			nex.flag=1;//把A的水倒空 
			judge(now,nex);
		}
		if(now.y>0)
		{
			nex.y=0;
			nex.x=now.x;
			nex.flag=2;//把B的水倒空 
			judge(now,nex);
			
		}
		if(now.x<A)
		{
			nex.x=A;
			nex.y=now.y;
			nex.flag=3;//给A加满 
			judge(now,nex);
			if(now.y!=0)
			{
				if(now.x+now.y<=A)
				{
					nex.x=now.x+now.y;//把B的水倒入A中 
					nex.y=0;
					nex.flag=4;
					judge(now,nex);
				}
				else
				{
					nex.x=A;
					nex.y=now.x+now.y-A;
					nex.flag=4;
					judge(now,nex);
				}
			}
		}
		if(now.y<B)
		{
			nex.y=B;
			nex.x=now.x;
			nex.flag=5;//B续满 
			judge(now,nex);
			if(now.x!=0)
			{
				if(now.x+now.y<=B)
				{
					nex.y=now.x+now.y;
					nex.x=0;
					nex.flag=6;//把A中的水倒入B中 
					judge(now,nex);
				}
				else
				{
					nex.y=B;
					nex.x=now.x+now.y-B;
					nex.flag=6;
					judge(now,nex);
				}
			}
		}
	}		
}
int main()
{
	int A,B,C;
	while(cin>>A>>B>>C)
	{
		bfs(A,B,C);
		cout<<"success"<<endl;
	}
	return 0;
}
发布了24 篇原创文章 · 获赞 9 · 访问量 7179

猜你喜欢

转载自blog.csdn.net/qq_40103496/article/details/104643747