倒水算法,c或者c++都可

问题描述

倒水算法,c或者c++都可

题目:倒水算法
1.指定水杯个数;
2.指定各个水杯的容量;
3.指定各水杯的当前水量;
4.倒水时遵循两个原则:a)将杯子倒满;b)将有水的杯子中的水全部倒干净。
5.最后达到指定的水平。

如有4个水杯,每个水杯的容量分别为21、11、8和5,目前装水分别为21、0、0和0,最终要求装水7、7、7和0.

解决方案

http://www.cnblogs.com/cyq1162/archive/2007/08/07/846552.aspx

解决方案二:

 //热门智力题 - 打水问题
//基本思想:用小桶容量的倍数对大桶的容量进行取余。
//指导方针:不断用小桶装水倒入大桶,大桶满了立即清空,
//每次判断下二个桶中水的容量是否等于指定容量。
#include<iostream>
#include <vector>
#include<string>
using namespace std;
const string OPERATOR_NAME[7] = {
    "装满A桶","装满B桶",
    "将A桶清空","将B桶清空",
    "A桶中水倒入B桶","B桶中水倒入A桶",
    "成功"
};
int main()
{
    cout<<"热门智力题 - 打水问题"<<endl;
    cout<<"  --by MoreWindows( http://blog.csdn.net/MoreWindows )--n"<<endl;

    int    a_volume, b_volume, goal_volume;
    vector<string> record;       //记录操作步数
    int    ai;
    int    i, a_water, b_water;

    cout<<"请输入A桶容量,B桶容量,目标容量:";
    cin>>a_volume>>b_volume>>goal_volume;
    a_water = b_water = 0; //A桶,B桶中有多少升水
    char szTemp[30];
    while (true)
    {
        if (a_water == 0)//A桶没水,就装满水
        {
            a_water = a_volume;
            sprintf(szTemp, "         A:%d  B:%d", a_water, b_water);
            record.push_back(OPERATOR_NAME[0] + szTemp);//fill A
        }
        else
        {
            //如果A桶的水比(B桶容量-B桶的水)要多
            if (a_water > b_volume - b_water)
            {
                //A桶的水==A桶的水+B桶的水-B桶容量
                a_water = a_water + b_water- b_volume;
                b_water = b_volume;      //B桶的水装满了
                sprintf(szTemp, "  A:%d  B:%d", a_water, b_water);
                record.push_back(OPERATOR_NAME[4] + szTemp);//A->B
                if (a_water == goal_volume)
                    break;
                b_water = 0;            //将B桶清空
                sprintf(szTemp, "       A:%d  B:%d", a_water, b_water);
                record.push_back(OPERATOR_NAME[3] + szTemp);
            }
            else
            {
                //B桶的水==A桶的水+B桶的水
                b_water += a_water;
                a_water = 0;
                sprintf(szTemp, "  A:%d  B:%d", a_water, b_water);
                record.push_back(OPERATOR_NAME[4] + szTemp);//A->B
                if (b_water == goal_volume)
                    break;
            }
        }
    }
    record.push_back(OPERATOR_NAME[6]); //success
    cout<<"n---------------------------------------------------"<<endl;
    cout<<"一个可行的倒水方案如下"<<endl;
    vector<string>::iterator pos;
    for (pos = record.begin(); pos != record.end(); pos++)
        cout<<*pos<<endl;
    cout<<"---------------------------------------------------"<<endl;
    return 0;
}

参考:http://www.acmerblog.com/pour-water-problem-5615.html

解决方案三:

package
{
public class PourWater
{
public function PourWater()
{
}

            public static const TAP:int        =        -1;                //        水龙头
            public static const OUT:int        =        -2;                //        倒掉水

            public static var vCupWater:Vector.<int>;
            public static var vVolume:Vector.<int>;
            public static var vTargetState:Vector.<int>;
            public static var iTargetWater:int;
            public static var iTargetCup:int;
            public static var vPath:Vector.<Path>;
            public static var bFind:Boolean;                

            public static function findShortPathEx( targets:Array, cupVolume:Array ):void
            {
                    vCupWater                =        new Vector.<int>( targets.length );
                    vTargetState        =        new Vector.<int>( targets.length );
                    vVolume                        =        new Vector.<int>( cupVolume.length );
                    bFind                        =        false;
                    for ( var i:int = 0; i < targets.length; ++i )
                    {
                            vTargetState[i]        =        targets[i];
                            vVolume[i]                =        cupVolume[i];
                    }
                    InitBfsState();
            }

            private static var vvAppearedState:Vector.<Vector.<int>>;
            private static var vvBfsQueue:Vector.<Vector.<int>>;
            private static var vvBfsPath:Vector.<Vector.<Path>>;
            private static var iBfsDepth:int        =        15;
            public static var iCurSteps:int        =        0;

            private static function InitBfsState():void
            {
                    vvAppearedState        =        new Vector.<Vector.<int>>;
                    vvBfsQueue                =        new Vector.<Vector.<int>>;
                    vvBfsPath                =        new Vector.<Vector.<Path>>;

                    for ( var i:int = 0; i < vVolume.length; ++i )
                    {
                            var tempstate:Vector.<int>        =        copyState( vCupWater );
                            pourWater( TAP, i, tempstate );
                            var tempVPath:Vector.<Path>        =        new Vector.<Path>;
                            tempVPath.push( new Path( TAP, i ) );
                            vvAppearedState.push( copyState( tempstate ) );
                            vvBfsQueue.push( tempstate );
                            vvBfsPath.push( tempVPath );
                            if ( isFind( tempstate ) )
                            {
                                    vPath        =        copyPath( tempVPath );
                                    bFind        =        true;
                                    return;
                            }
                    }

                    bfs();
            }

            private static function bfs():void
            {
                    while( vvBfsQueue.length > 0 )
                    {
                            var tempState:Vector.<int>        =        vvBfsQueue.shift();
                            var tempPath:Vector.<Path>        =        vvBfsPath.shift();
                            iCurSteps                                        =        tempPath.length;

                            if ( tempPath.length > iBfsDepth )
                                    return;
                            for ( var i:int = TAP; i < vVolume.length; ++i )
                            {
                                    for ( var j:int = 0; j < vVolume.length; ++j )
                                    {
                                            if ( i == j )
                                                    continue;
                                            var nextState:Vector.<int>        =        copyState( tempState );
                                            if ( pourWater( i, j, nextState ) && !isAppearedState( nextState ) )
                                            {
                                                    var nextPath:Vector.<Path>        =        copyPath( tempPath );
                                                    nextPath.push( new Path( i, j ) );

                                                    vvAppearedState.push( copyState( nextState ) );
                                                    vvBfsQueue.push( nextState );
                                                    vvBfsPath.push( nextPath );

                                                    trace("------------------------");
                                                    traceCurPath( nextPath );
                                                    traceCurState( nextState );
                                                    trace("------------------------");

                                                    if ( isFind( nextState ) )
                                                    {
                                                            vPath        =        copyPath( nextPath );
                                                            bFind        =        true;
                                                            return;
                                                    }
                                            }
                                    }
                            }

                            // 从杯子里往外倒水
                            for ( i = 0; i < vVolume.length; ++i )
                            {
                                    nextState        =        copyState( tempState );
                                    if ( nextState[i] > 0 )
                                    {
                                            nextState[i] = 0;
                                            if ( !isAppearedState( nextState ) )
                                            {
                                                    nextPath        =        copyPath( tempPath );
                                                    nextPath.push( new Path( i, OUT ) );

                                                    vvAppearedState.push( copyState( nextState ) );
                                                    vvBfsQueue.push( nextState );
                                                    vvBfsPath.push( nextPath );
                                            }
                                    }
                            }

                            tempState.length        =        0;
                            tempPath.length                =        0;
                            tempState                        =        null;
                            tempPath                        =        null;
                    }
            }

            private static function pourWater( iFromCup:int, iToCup:int, vCup:Vector.<int> ):Boolean
            {
                    // 目标满了
                    if ( vCup[iToCup] == vVolume[iToCup] )
                            return false;

                    if ( iFromCup != TAP )
                    {
                            // 源是空的
                            if ( vCup[iFromCup] == 0 )
                                    return false;
                            // 倒水
                            if ( vCup[iFromCup] >= ( vVolume[iToCup] - vCup[iToCup] ) )
                            {
                                    vCup[iFromCup]        =        vCup[iFromCup] - ( vVolume[iToCup] - vCup[iToCup] );
                                    vCup[iToCup]        =        vVolume[iToCup];
                            }
                            else
                            {
                                    vCup[iToCup]        =        vCup[iToCup] + vCup[iFromCup];
                                    vCup[iFromCup]        =        0;
                            }
                    }
                    else
                            vCup[iToCup]        =        vVolume[iToCup];

                    return true;
            }

            private static function isFind( state:Vector.<int> ):Boolean
            {
                    for ( var i:int = 0; i < state.length; ++i )
                            if ( vTargetState[i] != 0 && vTargetState[i] != state[i] )
                                    return false;
                    return true;
            }

            private static function isAppearedState( state:Vector.<int> ):Boolean
            {
                    for ( var i:int = 0; i < vvAppearedState.length; ++i )
                            if ( isEqualState( state, vvAppearedState[i]) )
                                    return true;
                    return false;
            }

            private static function isEqualState( stateSrc:Vector.<int>, stateDes:Vector.<int> ):Boolean
            {
                    for ( var i:int = 0; i < stateSrc.length; ++i )
                            if ( stateSrc[i] != stateDes[i] )
                                    return false;
                    return true;
            }

            private static function copyState( state:Vector.<int> ):Vector.<int>
            {
                    var resState:Vector.<int>        =        new Vector.<int>( state.length );
                    for ( var i:int = 0; i < state.length; ++i )
                            resState[i]        =        state[i];
                    return resState;
            }

            private static function copyPath( path:Vector.<Path> ):Vector.<Path>
            {
                    var resPath:Vector.<Path>        =        new Vector.<Path>( path.length );
                    for ( var i:int = 0; i < path.length; ++i )
                            resPath[i]                                =        new Path( path[i].iCupFrom, path[i].iCupTo );
                    return resPath;
            }

            public static function tracePath():String
            {
                    var res:String = "";
                    if ( bFind )
                    {
                            res += "找到长度为" + vPath.length + "的路径!" + "n";
                            for ( var i:int = 0; i < vPath.length; ++i )
                            {
                                    if ( vPath[i].iCupFrom == TAP )
                                            res += vVolume[vPath[i].iCupTo] + "L杯子到水龙头接水!" + "n";
                                    else if( vPath[i].iCupTo == OUT )
                                            res += vVolume[vPath[i].iCupFrom] + "L杯子倒掉水!" + "n";
                                    else
                                            res += vVolume[vPath[i].iCupFrom] + "L杯子往"+ vVolume[vPath[i].iCupTo] + "L杯子倒水!" + "n";
                            }
                    }
                    else
                            res += "经过深度为" + iCurSteps + "的广度优先搜索,没有找到结果!" + "n";

                    return res;
            }

            public static function traceCurState( state:Vector.<int> ):void
            {
                    var resStr:String        =        new String;
                    for ( var i:int = 0; i < state.length; ++i )
                            resStr += state[i] + "L#" + vVolume[i] + "L杯子,";
                    trace( resStr );
            }

            public static function traceCurPath( path:Vector.<Path> ):void
            {
                    var resStr:String        =        new String;
                    for ( var i:int = 0; i < path.length; ++i )
                    {
                            if ( path[i].iCupFrom == TAP )
                                    resStr += "水龙头" + "->" + vVolume[path[i].iCupTo] + "L杯子,";
                            else if( path[i].iCupTo == OUT )
                                    resStr += vVolume[path[i].iCupFrom] + "L杯子" + "倒掉水,";
                            else
                                    resStr += vVolume[path[i].iCupFrom] + "L杯子->" + vVolume[path[i].iCupTo] + "L杯子,";
                    }
                    trace( resStr );
            }
    }

}

时间: 2024-09-20 03:46:15

倒水算法,c或者c++都可的相关文章

倒水算法用c++实现。不知道怎么写。

问题描述 倒水算法用c++实现.不知道怎么写. 1.指定水杯个数: 2.指定各个水杯的容量: 3.指定各水杯的当前水量: 4.倒水时遵循两个原则:a)将杯子倒满:b)将有水的杯子中的水全部倒干净. 5.最后达到指定的水平. 如有4个水杯,每个水杯的容量分别为21.11.8和5,目前装水分别为21.0.0和0,最终要求装水7.7.7和0. 解决方案 使用深度优先算法进行暴力匹配.每次扩展以上两种操作,继续递归,直至目的结果出现后return. 手机码字,不写程序了,你可以直接搜一下类似的题目,例如

资源消耗异常,竟是因为比特币挖矿木马

上周末起,大规模网络勒索袭击迅速波及全球百余国家和地区,病毒锁死用户数据和电脑文件,要用户支付价值300-600美元的比特币赎金,成为刷屏级新闻.比特币是一种网络虚拟货币,主要基于一套密码编码.通过复杂算法产生,任何人都可以下载运行比特币客户端参与制造比特币,这个过程也被形象地称为"挖矿".而比特币"挖矿木马",就是由黑客通过木马控制大量肉鸡电脑,为其制造比特币的恶意程序. 警方缴获的比特币"挖矿机" 阿里云服务的客户中,就有中过招的.北京新华先

连日暴涨暴跌,比特币行情上演过山车

连日暴涨暴跌,比特币行情上演"过山车",而比特币投资热潮下潜伏的黑客风险也日益显现. 高配电脑沦为黑客挖矿"肉鸡".比特币大户屡遭盗号--根据360安全中心<2013年第三季度安全报告>显示,比特币投资者正面临比特币"挖矿木马".投资账户盗号以及交易市场沦陷三类威胁:而没有投资比特币.甚至完全不了解比特币的网民,也存在被木马控制电脑"挖矿"的风险.据了解,目前比特币"挖矿木马"家族正在急剧膨胀,

算法题:水杯倒水的问题

之前好像在博客园看到这样的题目: 1.有3个容器,各是20升,13升,7升, 形状不同也不透明.一开始20升的容器里面装了20升水,反正倒来倒去最后要让20升和13升容器各装了10升水 2. 2个外形不同的瓶子,各装800毫升水,另外还有1个300毫升的杯子 现在有4个人,不限制喝的次数,想办法让每个人都正好喝到400毫升水 第一第二道题目,口头说明解法就行了  第三个题,就是从第一第二题里面随便选择一个,使用编程来求解 于是乎..觉得有趣.便做了起来...花了一个下午的时间..终于做出来了:

openssl使用DSA算法生成签名

  命令: openssl> dgst -dss1 -sign C.pri -out signature.bin s.txt 解释 C.pri是DSA算法生成的私钥文件 s.txt是制作签名的原文 signature.bin是生成的签名文件 php中可以使用下面的方法察看签名内容  代码如下   <?php echo bin2hex(file_get_contents('signature.bin')); ?> 参考内容 消息摘要算法 支持的算法包括:MD2, MD4, MD5, MDC

数据结构教程 第三课 算法及算法设计要求

本课主题: 算法及算法设计要求 教学目的: 掌握算法的定义及特性,算法设计的要求 教学重点: 算法的特性,算法设计要求 教学难点: 算法设计的要求 授课内容: 一.算法的定义及特性 1.定义: ispass(int num[4][4]) { int i,j; for(i=0;i<4;i++) for(j=0;j<4;j++) if(num[i][j]!=i*4+j+1)/*一条指令,多个操作*/ return 0; return 1; }/*上面是一个类似华容道游戏中判断游戏是否结束的算法*/

java排序算法

Java 1.0和1.1库都缺少的一样东西是算术运算,甚至没有最简单的排序运算方法.因此,我们最好创建一个Vector,利用经典的Quicksort(快速排序)方法对其自身进行排序. 编写通用的排序代码时,面临的一个问题是必须根据对象的实际类型来执行比较运算,从而实现正确的排序.当然,一个办法是为每种不同的类型都写一个不同的排序方法.然而,应认识到假若这样做,以后增加新类型时便不易实现代码的重复利用. 程序设计一个主要的目标就是"将发生变化的东西同保持不变的东西分隔开".在这里,保持不

一种计算CD标识的算法

北京市167信箱(100036) 王亚军 ----本文介绍了关于音乐CD的红皮书格式.文章从如何根据数据格式,调用WindowsMCI接口函数,利用一定算法计算CD之ID号,用来唯一标识CD等方面阐述和说明,具有一定的应用价值. 一.红皮书格式 ----在光盘格式家族中,大家较熟悉的有红皮书.黄皮书.白皮书以及桔皮书等多种标准.这些格式有个共同的特点,就是光盘最小分配单位是长度为2352个字节的扇区:当然,并不是所有的2352个字节都可为用户所用,这要看具体是哪个标准.例如,黄皮书格式中2352

算法系列(十五) 循环和递归在算法中的应用

一.递归和循环的关系 1. 递归的定义 顺序执行.循环和跳转是冯·诺依曼计算机体 系中程序设计语言的三大基本控制结构,这三种控制结构构成了千姿百态的算法,程序,乃至整个软件世 界.递归也算是一种程序控制结构,但是普遍被认为不是基本控制结构,因为递归结构在一般情况下都可 以用精心设计的循环结构替换,因此可以说,递归就是一种特殊的循环结构.因为递归方法会直接或间接 调用自身算法,因此是一种比迭代循环更强大的循环结构. 2. 递归和循环实现的差异 循 环(迭代循环)结构通常用在线性问题的求解,比如多项