USACO-Section1.4 Mother's Milk【广度优先搜索】

来源:互联网 发布:涡流分选器淘宝 编辑:程序博客网 时间:2024/06/05 15:57

题目描述:

农民约翰有三个容量分别是A,B,C升的桶,A,B,C分别是三个从1到20的整数, 最初,A和B桶都是空的,而C桶是装满牛奶的。有时,农民把牛奶从一个桶倒到 另一个桶中,直到被灌桶装满或原桶空了。当然每一次灌注都是完全的。由于节约, 牛奶不会有丢失
写一个程序去帮助农民找出当A桶是空的时候,C桶中牛奶所剩量的所有可能性。(翻译来源:NOCOW)

INPUT FORMAT:

单独的一行包括三个整数A,B和C。

OUTPUT FORMAT:

只有一行,升序地列出当A桶是空的时候,C桶牛奶所剩量的所有可能性


SAMPLE INPUT 1

8 9 10


SAMPLE OUTPUT 1

1 2 8 9 10


SAMPLE INPUT 2

2 5 10


SAMPLE OUTPUT 2

5 6 7 8 9 10


解题思路:
这道题的中心思想就是广度优先遍历,从初状态开始,尝试a->b,a->c,b->a,b->c,c->a,c->b;如果状态已经经历过了,则返回。下面是代码。

#include<stdio.h>#include<string.h>#include<math.h>#include<stdlib.h>int a,b,c,v[20][20][20],ans[20];//v数组记录状态,ans数组记录结果int min(int a,int b){    return a<b?a:b;}void judge(int ta,int tb,int tc){    if(v[ta][tb][tc])return ;//如果该状态已被标记,则return    else{        v[ta][tb][tc]=1;        if(ta==0&&ans[tc]==0)ans[tc]=1;//如果a桶没有牛奶,则标记结果        if(ta!=0&&tb<b)//a->b        judge(ta-min(ta,b-tb),tb+min(ta,b-tb),tc);        if(ta!=0&&tc<c)//a->c        judge(ta-min(ta,c-tc),tb,tc+min(ta,c-tc));        if(tb!=0&&ta<a)//b->a        judge(ta+min(tb,a-ta),tb-min(tb,a-ta),tc);        if(tb!=0&&tc<c)//b->c        judge(ta,tb-min(tb,c-tc),tc+min(tb,c-tc));        if(tc!=0&&ta<a)//c->a        judge(ta+min(tc,a-ta),tb,tc-min(tc,a-ta));        if(tc!=0&&tb<b)//c->b        judge(ta,tb+min(tc,b-tb),tc-min(tc,b-tb));    }}int main() {    FILE *fin  = fopen ("milk3.in", "r");    FILE *fout = fopen ("milk3.out", "w");    fscanf(fin,"%d %d %d",&a,&b,&c);    int i,j;    judge(0,0,c);    for(i=0;i<c;i++)    if(ans[i])//由于c桶牛奶在初始状态下最多,所以以初始状态c桶牛奶数作为输出结尾    fprintf(fout,"%d ",i);    fprintf(fout,"%d\n",c);    exit(0);}
原创粉丝点击