BFS实现ABC水杯倒水问题

倒水问题
“fill A” 表示倒满A杯,"empty A"表示倒空A杯,“pour A B” 表示把A的水倒到B杯并且把B杯倒满或A倒空。
在这里插入图片描述
简单滴分析一下该题,首先由3个容器,我们能得到的水的体积无非是ABC三个数之间的运算,我们不妨将杯子容积设为x,y,因为C是目标体积,所以不做变量,那么就会有6种情况,每种情况下对应状况,我们就把操作记录下来。
在这里插入图片描述
Sample Input
2 7 5
2 7 4
照例把测试数据粘出来。
其实吧,我觉得代码还是有点bug,但是vj过了,emmmm,大家康康吧,顺便有错帮我指正出来^^
然后就是 你也可以这样理解μA+ λB=C, μ和 λ都是整数,可正可负,无非就是已知ABC,求 μ 和λ的整数解,可能答案不唯一,我在想用几何图形可不可以解决,不过呢,我好像不会,emmmm

#include<iostream>
#include<stdio.h>
#include<queue>
#include<map>
using namespace std;
struct cup{
 int x,y;int tag;
 bool operator <(const cup &c)const{
  return x!=c.x ? x<c.x : y<c.y;
 }
};
string str[6]={"fill A","empty A","fill B","empty B",
    "pour A B","pour B A"};
queue<cup> Q;
map<cup,cup> from;
void refresh(cup &s,cup &t){
 if(from.find(t) == from.end()){
  from[t]=s;
  Q.push(t);
 }
}
//void print()
void output(cup &cu){
 if(cu.x==0 && cu.y==0) return;
 output(from[cu]);
 cout<<str[cu.tag]<<endl;
}
void bfs(int A,int B,int C){
 cup cp,thenew;cp.x=0;cp.y=0;cp.tag=-1; 
 Q.push(cp);
 while(!Q.empty()){
  cup now=Q.front();
  Q.pop();//弹出
  if( now.x==C || now.y==C){ //终点 
   output(now);
   cout<<"success"<<endl;
   return;
  }
  if(now.x>0){ //将A杯置空 
   thenew.x=0;
   thenew.y=now.y;
   thenew.tag=1;
   refresh(now,thenew);
  }
  if(now.y>0){//如果是B被倒空 
   thenew.y=0;
   thenew.x=now.x;
   thenew.tag=3;
   refresh(now,thenew);
  }
  if(now.x<A){
   //如果A没有满,需要把B杯的水倒入A中
   thenew.x=A;thenew.y=now.y;
   thenew.tag=0;
   refresh(now,thenew);
   if(now.y != 0){
    if(now.x+now.y <=A){
     thenew.x=now.x+now.y;
     thenew.y=0;
     thenew.tag=5;
     refresh(now,thenew);
    }
    else{
     thenew.x=A;
     thenew.y=now.x+now.y-A;
     thenew.tag=5;
     refresh(now,thenew);
    }
   }
  }
  if(now.y<B){
   //当B需要被加满时,一直倒A
   thenew.y=B;
   thenew.x=now.x;
   thenew.tag=2;refresh(now,thenew);
   if(now.x != 0){
    if(now.y+now.x<=B){
     thenew.y=now.x+now.y;
     thenew.x=0;
     thenew.tag=4;
     refresh(now,thenew);
    }
    else{
     thenew.x=now.x+now.y-B;
     thenew.y=B;thenew.tag=4;
     refresh(now,thenew);
    }
   } 
  }
 }
 
}
int main(){
 int A,B,C;
 while(scanf("%d%d%d",&A,&B,&C) != EOF){
  if(C==0){
   cout<<"empty A"<<endl;
   cout<<"success"<<endl;
  }
  bfs(A,B,C);
 }
 return 0;
}

今天不知道怎么肥四,代码不能整体粘贴上来,只好一段一段地粘了。

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值