90. 奇妙货币交易问题| 豆包MarsCode AI刷题

111 阅读2分钟

90.奇妙货币交易问题

题目用python通过,如有需要请用ai转义成其他代码,由于这道题用数学解答,代码没有太复杂,看看自己写也成。



解题思路:

第一思路:

暴力模拟,直接干。 让marscode帮我们生成暴力的代码。

但是marscode的代码tle了,因为递归的问题。

再让他修改一下,这次V = 10,W = 9改成了dp,但是只通过了样例三。那就分析下样例1 和样例2的特点把 。

样例1 :V = 10,W = 9。 打印出 yes。 交易需要自己掏出来一张 10 ,卖家找回 1 个 1. 样例2 :V = 200,W = 40199。 打印出 yes。 交易需要自己掏出 40000 和 200 ,卖家找回 2 个 1 。

这里被判断为no主要是没处理找钱的情况,只考虑了掏钱的情况。明白了原因,把错误发给豆包,让豆包优化一下。

但是还是有个样例没过。 那好吧只能自己推倒了。


第二思路:

再读一遍题目。 每次最多能用两张面值相同的纸币。 那么对于每张限定面值的纸币可以分5种情况:

  • 第一种: 自己掏出来 2 张这种纸币
  • 第二种: 自己掏出来 1 张这种纸币
  • 第三种: 自己掏出来 0 张这种纸币
  • 第四种: 卖家找回 1 张这种纸币
  • 第五种: 卖家找回 2 张这种纸币

对于每张纸币,总共有5种处理情况。 那我们要枚举每种纸币的情况。但是要考虑一下我们要枚举到多大的纸币面值。

对于样例 V= 20, w = 199 ,需要一个超过当前面值的纸币200才能解决这个样例。 于是我们可以将循环套件变大一些。
还好有 python 模运算的特性,可以让我们不用关心负数的模出现的问题。 可以直接对负数取模得到正数。那么就不用考虑面值超过当前值的情况了。

对于枚举顺序, 我们可以从高位开始, 依次处理 V 进制下 W 的每一位。 遍历每一位进制下纸币出现的五种情况, 如果可以在 5 种情况下找出当前位置的找钱方案, 那么可以继续运行。如果某一进制在5种情况下都不满足, 那么当前数额是没办法找到解决方案的,直接返回 no 。

对于可以找钱的方案, W 循环结束会变成0 , 直接返回YES。


通过代码如下:
def solution(V, W):
    if V == 1:
        return "YES"
    while W > 0:
        for i in range(-2, 3):
            digit = (W + i) % V
            if digit == 0:
                W //= V
                break
        else:
            return 'NO'
    return 'YES'