純美蘋果園

TRPG討論區 => 研討區 => 5版 討論區 => 主题作者是: Eygma 于 2024-09-25, 周三 19:36:17

主题: 延寿药水:喝几瓶能保证老死?
作者: Eygma2024-09-25, 周三 19:36:17
引用
延寿药水Potion of Longevity
药水,极珍稀
饮用此药水后,你的生理年龄减少1d6+6岁,药水最低将你降低至13岁。此后每当你再次饮这种药水时,都会累加10%的概率令你增加1d6+6岁,而非减少。这种琥珀色药水中看似悬浮着一条蝎子的尾巴、一颗蝰蛇的牙、一只死蜘蛛,以及一颗违反常理地跳动着的小心脏。药水瓶被打开时,这些成分都将无影无踪。

灵感来自于之前群友关于人类喝多少延寿药水必定能老死的讨论,做了个脚本:
引用
请输入测试次数:50
请输入初始年龄(不能低于13岁):24
请输入预期寿命上限:80

第 1 次测试: 饮用了 15 瓶药水后,年龄达到了 84 岁。
第 2 次测试: 饮用了 16 瓶药水后,年龄达到了 81 岁。
……

50 次测试的平均饮用次数: 14.00 瓶药水
以种族平均预期寿命的30%作为初始寿命,人类喝14瓶左右基本就能确保老死,精灵则是66瓶,矮人是33瓶。
嗯,真是完全用不上的研究啊()

代码:
import random

def drink_potion(age, is_first_time, aging_chance):
    if is_first_time:
        # 第一次喝药水必定年轻
        age -= random.randint(1, 6) + 6
        age = max(age, 13) 
        return age, False, aging_chance
    else:
        if random.random() <= aging_chance:
            # 衰老
            age += random.randint(1, 6) + 6
        else:
            # 年轻
            age -= random.randint(1, 6) + 6
            age = max(age, 13) 
       
        # 增加10%衰老概率
        aging_chance += 0.1
        return age, False, aging_chance

def simulate_drinking_potion(initial_age, max_age, max_trials=1000):
    age = initial_age
    is_first_time = True
    aging_chance = 0.1
    trials = 0
   
    while age <= max_age and trials < max_trials:
        age, is_first_time, aging_chance = drink_potion(age, is_first_time, aging_chance)
        trials += 1
        if age > max_age:
            break
   
    return trials, age

def run_multiple_simulations(test_count, initial_age, max_age):
    total_trials = 0
    for i in range(test_count):
        trials, final_age = simulate_drinking_potion(initial_age, max_age)
        print(f"第 {i + 1} 次测试: 饮用了 {trials} 瓶药水后,年龄达到了 {final_age} 岁。")
        total_trials += trials
   
    average_trials = total_trials / test_count
    print(f"\n{test_count} 次测试的平均饮用次数: {average_trials:.2f} 瓶药水")

def main():
    while True:
        try:
            test_count = int(input("请输入测试次数:"))
            initial_age = int(input("请输入初始年龄(不能低于13岁):"))
            if initial_age < 13:
                print("初始年龄不能低于13岁,请重新输入!")
                continue
            max_age = int(input("请输入预期寿命上限:"))
        except ValueError:
            print("输入无效,请输入整数!")
            continue
       
        run_multiple_simulations(test_count, initial_age, max_age)
       
        action = input("\n输入“1”重新输入参数,输入“0”退出程序: ").strip().lower()
        if action == '0':
            print("程序已退出。")
            break

main()
主题: Re: 延寿药水:喝几瓶能保证老死?
作者: \星尘/2024-09-25, 周三 21:06:31
1824. D&D延寿药水问题
在DND中,神奇的延寿药水可以改变饮用者的年龄。一位法师想要确定某个生物需要喝多少瓶这种药水才能确保死于老年。

药水规则:

给定:
- max_age: 生物的种族寿命极限
- current_age: 生物的当前年龄

要求:
编写一个函数 min_potions_to_die_of_old_age(max_age: int, current_age: int) -> int,
计算这个生物最少需要喝多少瓶药水才能确保活到寿命极限。如果不可能达到寿命极限,返回-1。

注意:
- 初始年龄按种族平均预期寿命的30%计算,即 current_age = int(max_age * 0.3)
- 使用伪随机数生成器模拟1d6的效果
- 考虑边界情况和概率累积效果

示例:
引用
输入: max_age = 100, current_age = 30
输出: 6
解释:
抽样模拟运行:
药水1: 30 -> 19 (减少11岁)
药水2: 19 -> 13 (本应减少9岁,但最低只能到13岁)
药水3: 13 -> 23 (20%概率变老,增加10岁)
药水4: 23 -> 13 (减少10岁)
药水5: 13 -> 22 (30%概率变老,增加9岁)
药水6: 22 -> 34 (40%概率变老,增加12岁)
之后继续饮用,年龄会稳定增长至100岁

约束:
50 <= max_age <= 1000
13 <= current_age < max_age

进阶:
你能优化算法以处理更大范围的max_age(如max_age <= 10^9)吗?

代码: [选择]
import random


def min_potions_to_die_of_old_age(max_age: int, current_age: int) -> int:
    def simulate_potion_effect(age: int, aging_chance: float) -> int:
        if random.random() < aging_chance:
            return age + random.randint(1, 6) + 6
        return max(13, age - random.randint(1, 6) - 6)

    potions = 0
    aging_chance = 0.0

    while current_age < max_age and potions < 10000:  # 防止无限循环
        potions += 1
        current_age = simulate_potion_effect(current_age, aging_chance)
        aging_chance = min(1.0, aging_chance + 0.1)

    return potions if current_age >= max_age else -1

# 测试代码


def test_min_potions():
    test_cases = [
        (80, 24),
        (200, 60),
        (500, 150),
        (1000, 300),
    ]

    for max_age, current_age in test_cases:
        result = min_potions_to_die_of_old_age(max_age, current_age)
        print(f"种族寿命: {max_age}, 当前年龄: {current_age}, 最少需要的药水数: {result}")


# 运行测试
random.seed(42)  # 设置随机种子以获得可重复的结果
test_min_potions()

引用
py test.py
种族寿命: 80, 当前年龄: 24, 最少需要的药水数: 14
种族寿命: 200, 当前年龄: 60, 最少需要的药水数: 23
种族寿命: 500, 当前年龄: 150, 最少需要的药水数: 52
种族寿命: 1000, 当前年龄: 300, 最少需要的药水数: 88

主题: Re: 延寿药水:喝几瓶能保证老死?
作者: 希尔2024-09-25, 周三 21:30:20
【必定】难道不是考虑极值:
初始喝11瓶确保负面概率达到100%且13岁出门,之后每次+7
得出结果 [11+(最大年龄-13)/7] 向上取整
主题: Re: 延寿药水:喝几瓶能保证老死?
作者: 冰原上的咸喵2024-09-25, 周三 22:35:08
我记得我打开的是果园啊,怎么到力扣了 :em032
主题: Re: 延寿药水:喝几瓶能保证老死?
作者: EternalRider2024-09-26, 周四 16:35:36
我懵逼了半天才意识到题目意思是一口气喝多少瓶能当场老死……
主题: Re: 延寿药水:喝几瓶能保证老死?
作者: 银发三千雪满头2024-09-27, 周五 02:25:38
果然强度的尽头是敲matlab :em032