# POJ 3414 Pots

2098人阅读 评论(0)

Pots
Time Limit: 1000MS Memory Limit: 65536K
Total Submissions: 6326 Accepted: 2642Special Judge
Description

You are given two pots, having the volume of A and B liters respectively. The following operations can be performed:

FILL(i)        fill the pot i (1 ≤ i ≤ 2) from the tap;
DROP(i)      empty the pot i to the drain;
POUR(i,j)    pour from pot i to pot j; after this operation either the pot j is full (and there may be some water left in the pot i), or the pot i is empty (and all its contents have been moved to the pot j).
Write a program to find the shortest possible sequence of these operations that will yield exactly C liters of water in one of the pots.

Input

On the first and only line are the numbers A, B, and C. These are all integers in the range from 1 to 100 and C≤max(A,B).

Output

The first line of the output must contain the length of the sequence of operations K. The following K lines must each describe one operation. If there are several sequences of minimal length, output any one of them. If the desired result can’t be achieved, the first and only line of the file must contain the word ‘impossible’.

Sample Input

3 5 4
Sample Output

6
FILL(2)
POUR(2,1)
DROP(1)
POUR(2,1)
FILL(2)
POUR(2,1)
Source

Northeastern Europe 2002, Western Subregion

FILL（1）表示倒满1杯子，POUR（2，1）表示将2杯子里的水倒进1杯子中，DROP（1）表示倒空1杯子。

#include<iostream>
#include<cstdio>
#include<cstring>
using namespace std;

int a,b,c;

struct node
{
int aa;//a杯子里的水量
int bb;//b杯子里的水量
int parent;//父节点编号
int ope;//执行什么操作得到该节点
int level;//层次
node(int x,int y,int p,int o,int l):aa(x),bb(y),parent(p),ope(o),level(l){}//构造函数，为了方便返回该结构体变量
node(){}//有自定义构造函数的时候必须有一个默认构造函数
};

node nod[1000000];
bool fl[205][205];
int stk[1000000];

void output(int p)
{
int top=0;
stk[0]=p;//数组模拟栈实现递归
while(nod[stk[top]].parent!=-1)
{
top++;
stk[top]=nod[stk[top-1]].parent;
}
for(int i=top;i>=0;i--)
{
switch(nod[stk[i]].ope)
{
case 0:
{
printf("DROP(1)\n");
}
break;
case 1:
{
printf("FILL(1)\n");
}
break;
case 2:
{
printf("DROP(2)\n");
}
break;
case 3:
{
printf("FILL(2)\n");
}
break;
case 4:
{
printf("POUR(1,2)\n");
}
break;
case 5:
{
printf("POUR(2,1)\n");
}
break;
}
}
}

void f1(node& n)
{
n.aa=0;
}
void f2(node& n)
{
n.aa=a;
}
void f3(node& n)
{
n.bb=0;
}
void f4(node&n)
{
n.bb=b;
}
void f5(node&n)
{
if(b-n.bb<n.aa)
{
n.aa=n.aa-(b-n.bb);
n.bb=b;
}
else
{
n.bb+=n.aa;
n.aa=0;
}
}
void f6(node&n)
{
if(a-n.aa<n.bb)
{
n.bb=n.bb-(a-n.aa);
n.aa=a;
}
else
{
n.aa+=n.bb;
n.bb=0;
}
}
void(*fun[6])(node&n)={f1,f2,f3,f4,f5,f6};//函数指针数组，保存六个函数

int main()
{
while(~scanf("%d%d%d",&a,&b,&c))
{
memset(fl,0,sizeof(fl));//标记数组，表示一种状态是否出现过
int front=0;
int tail=0;
nod[tail++]=node(0,0,-1,-1,0);//构造函数的用处
fl[0][0]=1;
int res;
int res_loc=-1;
while(front<tail)
{
node nd=nod[front++];
if(nd.aa==c||nd.bb==c)
{
res=nd.level;//res记录得到结果时候的深度
res_loc=front-1;//表示得到的结果在数组中是第几个
break;
}
for(int i=0;i<6;i++)//进行六种操作，每次调用函数数组中的一个函数
{
node nt=nd;
fun[i](nt);//调用第i个函数
if(fl[nt.aa][nt.bb]==0)
{
fl[nt.aa][nt.bb]=1;
nod[tail++]=node(nt.aa,nt.bb,front-1,i,nt.level+1);//依然是构造函数的应用
}
}
}
if(res_loc==-1)
{
printf("impossible\n");
continue;
}
printf("%d\n",res);
output(res_loc);
}
return 0;
}


0
0

* 以上用户言论只代表其个人观点，不代表CSDN网站的观点或立场
个人资料
• 访问：46984次
• 积分：920
• 等级：
• 排名：千里之外
• 原创：44篇
• 转载：9篇
• 译文：0篇
• 评论：9条
评论排行
最新评论