10元最多可喝多少瓶啤酒?(不可借酒+可借酒)

背景

《爱情公寓5》中有个剧情:每瓶啤酒2元,2个空酒瓶或4个瓶盖可换1瓶啤酒。10元最多可喝多少瓶啤酒?
脑海模拟起来的确有点费劲。心算结果是15瓶,而剧情实践居然是20瓶!结合弹幕说的酒吧可能可以借酒,故猜测借酒使最终喝了20瓶。
如果改变拥有的钱数或啤酒价格时,答案又是什么呢?
此时,不禁想用编程的方法解决一下。

思路

分两种情况:酒吧可以借酒;酒吧不可以借酒;

酒吧不可以借酒

此时,当剩余酒盖数<4且剩余空瓶数<2时,计算就结束了

酒吧可以借酒

这种情况比较麻烦,需要考虑1个空瓶和3个瓶盖时借一瓶酒的情况。此时,当换完酒、假设喝了酒并把酒瓶换新酒、喝了新酒之后(空瓶1,瓶盖3),手上的酒瓶和酒盖的价值不大于已借的酒瓶数(2瓶)时,就需要考虑结束计算了。
详细代码如下:

//
//  main.swift
//  beerMaxDrink
//
//  Created by on 2020/2/4.
//  Copyright ? 2020. All rights reserved.
//
/*
 酒吧啤酒2元一瓶,两个空瓶或四个瓶盖可以换一瓶啤酒(酒吧概不借酒),你有10元钱,请问最多可以喝几瓶?
 */

import Foundation

//共累计喝的瓶数
var drinkSum = 0
//当前瓶子数
var bottleNum = 0
//当前瓶盖数
var capsNum = 0

//返回(累计喝瓶数,剩余瓶子数,剩余瓶盖数)
func getMaxDrinkSum(money:Float, price:Float) ->(Int, Int, Int) {

    bottleNum = Int(money / price)
    capsNum = bottleNum
    drinkSum = bottleNum

    //开始换酒,是个循环
    while bottleNum > 1 || capsNum > 3 {
        //酒瓶换
        let wineAddedByBottle = bottleNum / 2
        drinkSum += wineAddedByBottle
        bottleNum = bottleNum % 2 + wineAddedByBottle
        capsNum += wineAddedByBottle

        //酒盖换
        let wineAddedByCaps = capsNum / 4
        drinkSum += wineAddedByCaps
        capsNum = capsNum % 4 + wineAddedByCaps
        bottleNum += wineAddedByCaps
    }
    return (drinkSum, bottleNum, capsNum)
}

//可以借酒时,返回(累计喝瓶数,剩余瓶子数,剩余瓶盖数)
func getMaxDrinkSumCanBorrow(money:Float, price:Float) ->(Int, Int, Int) {

    var borrowedNum = 0
    bottleNum = Int(money / price)
    capsNum = bottleNum
    drinkSum = bottleNum

    //开始换酒,是个循环
    while bottleNum >= 1 || capsNum >= 3 {

        //酒瓶换
        let wineAddedByBottle = bottleNum / 2
        drinkSum += wineAddedByBottle
        bottleNum = bottleNum % 2 + wineAddedByBottle
        capsNum += wineAddedByBottle

        //如果(2酒瓶2酒盖时,"酒瓶换"已经把2酒瓶换为1瓶1盖,即变为1瓶3盖)借一瓶后,空瓶和瓶盖能换的酒数 <= 已借瓶数时,结束;否则,借一瓶
        if 1 == bottleNum || 3 == capsNum{//不能少,否则在循环时会提前借酒
            if (bottleNum + 1)/2 + (capsNum + 1)/4 <= borrowedNum {

                //不应该喝一瓶,回退
                bottleNum += 1
                capsNum -= 1
                return (drinkSum - 1, bottleNum - borrowedNum, capsNum - borrowedNum)
            }else{ //借一瓶
                borrowedNum += 1
                bottleNum += 1
                capsNum += 1

                //酒瓶换
                let wineAddedByBottle = bottleNum / 2
                drinkSum += wineAddedByBottle
                bottleNum = bottleNum % 2 + wineAddedByBottle
                capsNum += wineAddedByBottle
            }
        }

        //酒盖换
        let wineAddedByCaps = capsNum / 4
        drinkSum += wineAddedByCaps
        capsNum = capsNum % 4 + wineAddedByCaps
        bottleNum += wineAddedByCaps
    }
    return (drinkSum, bottleNum, capsNum)
}

for i in 0..<20{
    let rslt0 = getMaxDrinkSum(money: Float(i), price: 2)
    print("-----------------------")
    print("\(i)元:不能借酒:\(rslt0)")

    let rsltCanBorrow0 = getMaxDrinkSumCanBorrow(money: Float(i), price: 2)
    print("能借酒:\(rsltCanBorrow0)")
}

let rslt1 = getMaxDrinkSum(money: 10.0, price: 5)

print("-----------------------")
print("酒价格5元时,不能借酒:\(rslt1)")

let rsltCanBorrow1 = getMaxDrinkSumCanBorrow(money: 10.0, price: 5)
print("能借酒:\(rsltCanBorrow1)")

运行结果如下,证明代码正确。且可以看出规律:可以借酒时,一般比不能借酒时,可以多喝5瓶酒:

-----------------------
0元:不能借酒:(0, 0, 0)
能借酒:(0, 0, 0)
-----------------------
1元:不能借酒:(0, 0, 0)
能借酒:(0, 0, 0)
-----------------------
2元:不能借酒:(1, 1, 1)
能借酒:(4, 0, 0)
-----------------------
3元:不能借酒:(1, 1, 1)
能借酒:(4, 0, 0)
-----------------------
4元:不能借酒:(3, 1, 3)
能借酒:(8, 0, 0)
-----------------------
5元:不能借酒:(3, 1, 3)
能借酒:(8, 0, 0)
-----------------------
6元:不能借酒:(7, 1, 3)
能借酒:(12, 0, 0)
-----------------------
7元:不能借酒:(7, 1, 3)
能借酒:(12, 0, 0)
-----------------------
8元:不能借酒:(11, 1, 3)
能借酒:(16, 0, 0)
-----------------------
9元:不能借酒:(11, 1, 3)
能借酒:(16, 0, 0)
-----------------------
10元:不能借酒:(15, 1, 3)
能借酒:(20, 0, 0)
-----------------------
11元:不能借酒:(15, 1, 3)
能借酒:(20, 0, 0)
-----------------------
12元:不能借酒:(19, 1, 3)
能借酒:(24, 0, 0)
-----------------------
13元:不能借酒:(19, 1, 3)
能借酒:(24, 0, 0)
-----------------------
14元:不能借酒:(23, 1, 3)
能借酒:(28, 0, 0)
-----------------------
15元:不能借酒:(23, 1, 3)
能借酒:(28, 0, 0)
-----------------------
16元:不能借酒:(27, 1, 3)
能借酒:(32, 0, 0)
-----------------------
17元:不能借酒:(27, 1, 3)
能借酒:(32, 0, 0)
-----------------------
18元:不能借酒:(31, 1, 3)
能借酒:(36, 0, 0)
-----------------------
19元:不能借酒:(31, 1, 3)
能借酒:(36, 0, 0)
-----------------------
酒价格5元时,不能借酒:(3, 1, 3)
能借酒:(8, 0, 0)
Program ended with exit code: 0

原文地址:https://www.cnblogs.com/Dast1/p/12262231.html

时间: 2024-10-10 23:46:25

10元最多可喝多少瓶啤酒?(不可借酒+可借酒)的相关文章

每瓶啤酒2元,2个空酒瓶或4个瓶盖可换1瓶啤酒。10元最多可喝多少瓶啤酒? php

//根据题意设定初始变量值//然后 一个while循环去操作//每换得一个瓶子,换的那个减去要做相应的数目//然后喝了啤酒后, 各数量加1//直到不符合要求.跳出循环 1 class Beer{ 2 3 protected $uni_gai = 4; //每4个瓶盖1瓶 4 protected $uni_bottle = 2; //每两个瓶子换1瓶 5 protected $uni_beer = 2; //每瓶2块钱 6 protected $rs = array();//存取结果 7 prot

啤酒2块一瓶,4个瓶盖可换1瓶,2个空瓶可换1瓶,10块钱可以喝多少瓶?

1.编程的写法: using System; using System.Collections.Generic; using System.Text; namespace SlowX.CalcEgg { class Program { protected static string ShowStr(int theResult, int KP, int PG) { return theResult + "瓶啤酒." + KP + "空瓶." + PG + "

可以喝多少瓶啤酒

可以喝多少瓶啤酒 问题 4个瓶盖,或者2个酒瓶,可以换一瓶啤酒, 现在有10块钱,啤酒2块钱一瓶,问: 共可以喝多少瓶啤酒? 解法一 问题分析 手里有10块钱,既然要喝尽可能多的啤酒,就要买尽可能的多买,所以直接全部买成啤酒,共可买5瓶.现在共有5瓶啤酒,那么可以进行以下的操作(序号越低,优先级越高): 如果有酒,则全部喝掉: 如果有 >= 4个瓶盖,则换成 n/4 瓶啤酒: 如果有 >= 2个酒瓶,则换成 n/2 瓶啤酒: 显然,如果用程序模拟,实现起来很简单. 结果 代码: # encod

javascript计算啤酒2元一瓶,4个盖换一瓶,2个瓶换一瓶,10元钱最多喝多少瓶

var n = 0//当前剩下多少瓶加上喝赢了多少瓶 var x = 5//初始多少瓶 var y = 0//除了喝掉的,剩下多少瓶 var z = 0;//总数 var arr = []//定义一个数组存放值 arr.push(x);//先把最初始瓶数添加到数组 //程序1 var fn = function(s){ y = s -4; //剩下多少瓶 s = y + parseInt(s/4) + parseInt(s/2);//剩下多少瓶加上赢了多少瓶 n = s//赋值给上面的n arr

1 元钱买一瓶汽水,两个空汽水瓶换一瓶汽水。现有 20 元钱,问最多可以喝到多少瓶汽水?

答案一:20+10+5+2+ 1+ 1= 39瓶 答案二:20+ 10+ 5+ 2+ 1+ 1+ 1= 40 一开始 20瓶没有问题,随后的 10瓶和 5瓶也都没有问题,接着把 5瓶分成 4瓶和 1瓶,前 4个空瓶再换 2瓶,喝完后 2瓶再换 1瓶,此时喝完后手头上剩余的空瓶数为 2个,把这 2个瓶 换 1瓶继续喝,喝完后把这 1个空瓶换 1瓶汽水,喝完换来的那瓶再把瓶子还给人家即可,所以最多可以喝的汽水数为: 20+ 10+ 5+ 2+ 1+ 1+ 1= 40.但是题目中并没有说可以赊账,因此

给20块钱买可乐,每瓶可乐3块钱,喝完之后退瓶子可以换回1块钱,问最多可以喝到多少瓶可乐

package com.Summer_0417.cn; /** * @author Summer * 给20块钱买可乐,每瓶可乐3块钱,喝完之后退瓶子可以换回1块钱,问最多可以喝到多少瓶可乐. */public class Test_Method12 { public static void main(String[] args) { int money = 20, price = 3; // bottle表示每一次购买的可乐瓶数 int bottle = 0; // change表示每次购买完

程序猿,你也配吃10元的盒饭?

“你也配吃10元的盒饭?”作者:yxixhdfqwe 又是一个阳光灿烂的中午,看了一上午的报纸,茶水也顺带喝了不少,肚子早已经咕咕作响了,今天中午吃点什么了,貌似楼下的新开张的盒饭还不错,于是我来到楼下准备买上一盒.   菜色还不错,价格有6元,8元,10元,12元,20元的,像哥这样的精英管理人才,怎么着也的吃最高级的才配合身份,就在我准备购买时,一个响亮的声音响起,   "老板,给我一份10元的盒饭",   顺势撇了一眼,一个小伙子,眉开眼笑的靠近盒饭铺,今天是1号,看样子是发工资

Android:刚6瓶啤酒4两56度白酒下肚,居然20分钟做了一手机版网站 !

刚6瓶啤酒4两56度白酒下肚,居然20分钟不到时间做了一手机版网站 !人有多大潜力你知道吗? 大家有兴趣的可以用手机或微信打开 http://xh.yunxunmi.com/ 看看俺这酒后之做! 更多0

滴滴过节送10元打车券是不是bug

自从滴滴跟快的去年合作以后,也不玩烧钱大战了,也没法打到免费的车了,乘客打车优惠也少了. 但是现在的滴滴在过节的时候还是会返滴滴代金券,而且金额都比较大,超出了打车的起步价.半年前这边的司机会经常利用司机版的APP刷单,从而将滴滴跟快的的打车券赚去,虽然腾讯和阿里对“刷单”现象处理的很严,比如,同一个乘客一天不能打同样的司机版APP.同一个乘客不能每天打一个司机版APP的车.司机版APP每个月接单数量不得超过一定限制等.但是,这种“刷单”现象并未完全根除. 刷单方式,个人感觉其实是有多种,但最终