HDU 1495 非常可乐
Problem Description
大家一定觉的运动以后喝可乐是一件很惬意的事情,但是seeyou却不这么认为。因为每次当seeyou买了可乐以后,阿牛就要求和seeyou一起分享这一瓶可乐,而且一定要喝的和seeyou一样多。但seeyou的手中只有两个杯子,它们的容量分别是N 毫升和M 毫升 可乐的体积为S (S<101)毫升 (正好装满一瓶) ,它们三个之间可以相互倒可乐 (都是没有刻度的,且 S==N+M,101>S>0,N>0,M>0) 。聪明的ACMER你们说他们能平分吗?如果能请输出倒可乐的最少的次数,如果不能输出"NO"。
Input
三个整数 : S 可乐的体积 , N 和 M是两个杯子的容量,以"0 0 0"结束。
Output
如果能平分的话请输出最少要倒的次数,否则输出"NO"。
Sample Input
7 4 3
4 1 3
0 0 0
Sample Output
NO
3
题目思路:
bfs搜索6中可能性
代码:
//hdu 1495
#include<iostream>
#include<queue>
#include<string>
using namespace std;
int s, m, n;
struct Node {
int ls,lm, ln; //表示三个容器中剩余水量
int found;
int cnt;
Node(int s, int m, int n, int cnt) {
this->ls = s, this->lm = m, this->ln = n, this->cnt = cnt;
}
};
const int INF = 1e5;
int visit[101][101][101];
int found;
void bfs()
{
for (int i = 0; i <= s; i++)
for (int j = 0; j <= m; j++)
for (int k = 0; k <= n; k++)
visit[i][j][k] = 0;
queue<Node> q;
found = 0; //初始化没找到
visit[s][0][0] = 1;
Node node(s, 0, 0, 0);
q.push(node);
while (!q.empty())
{
Node t = q.front();
q.pop();
if (found || t.ls == t.lm && t.ln==0 || t.lm == t.ln && t.ls==0|| t.ln == t.ls &&t.lm==0) {
found = 1;
printf("%d\n", t.cnt);
return;
}
//下方的6个if语句可以写成循环,看了别人的题解才发现
//int ds[6] = {0, 0, 1, 1, 2, 2};
//int de[6] = { 1, 2, 0, 2, 0, 1 };
//turn[i]表示ds->de,从一个杯子倒到另一个杯子
int ts, tm, tn;
if (t.ls != 0)
{
//s->m
tm = (t.ls + t.lm) / m ? m : t.ls + t.lm;
ts = (t.ls + t.lm) / m ? t.ls + t.lm - m : 0;
tn = t.ln;
if (!visit[ts][tm][tn] && ts >= 0 && ts <= s && tm >= 0 && tm <= m && tn >= 0 && tn <= n) {
visit[ts][tm][tn] = 1;
q.push(Node(ts, tm, tn, t.cnt + 1));
}
//s->n
tn = (t.ls + t.ln) / n ? n : t.ls + t.ln;
ts = (t.ls + t.ln) / n ? t.ls + t.ln - n : 0;
tm = t.lm;
if (!visit[ts][tm][tn] && ts >= 0 && ts <= s && tm >= 0 && tm <= m &&tn >= 0 && tn <= n) {
visit[ts][tm][tn] = 1;
q.push(Node(ts, tm, tn, t.cnt + 1));
}
}
if (t.lm != 0)
{
//m->s
tm = 0, ts = t.ls + t.lm;
tn = t.ln;
if (!visit[ts][tm][tn] && ts >= 0 && ts <= s && tm >= 0 && tm <= m && tn >= 0 && tn <= n) {
visit[ts][tm][tn] = 1;
q.push(Node(ts, tm, tn, t.cnt + 1));
}
//m->n
tn = (t.lm + t.ln) / n ? n : t.lm + t.ln;
tm = (t.lm + t.ln) / n ? t.lm + t.ln - n : 0;
ts = t.ls;
if (!visit[ts][tm][tn] && ts >= 0 && ts <= s && tm >= 0 && tm <= m && tn >= 0 && tn <= n) {
visit[ts][tm][tn] = 1;
q.push(Node(ts, tm, tn, t.cnt + 1));
}
}
if (t.ln != 0)
{
//n->s
tn = 0, ts = t.ls + t.ln;
tm = t.lm;
if (!visit[ts][tm][tn] && ts >= 0 && ts <= s && tm >= 0 && tm <= m && tn >= 0 && tn <= n) {
visit[ts][tm][tn] = 1;
q.push(Node(ts, tm, tn, t.cnt + 1));
}
//n->m
tm = (t.ln + t.lm) / m ? m : t.ln + t.lm;
tn = (t.lm + t.ln) / m ? t.lm + t.ln - m : 0;
ts = t.ls;
if (!visit[ts][tm][tn] && ts >= 0 && ts <= s && tm >= 0 && tm <= m && tn >= 0 && tn <= n) {
visit[ts][tm][tn] = 1;
q.push(Node(ts, tm, tn, t.cnt + 1));
}
}
}
}
int main()
{
while (cin >> s >> m >> n, s, m, n)
{
bfs();
if (!found)printf("NO\n");
}
return 0;
}