基于输入参数模拟滚动骰子的Python函数1)骰子数2)滚动数

2024-10-08 23:18:08 发布

您现在位置:Python中文网/ 问答频道 /正文

我一直在查看stack,花了几个小时浏览,试图解决这个问题。 任务是:
编写一个名为dicerolls的Python函数来模拟掷骰子。你的函数应该有两个参数:掷骰子的次数k和掷骰子的次数n。该函数应模拟随机滚动k个骰子n次,跟踪每个总面值。然后,它应该返回一个字典,其中包含每个可能的总面值出现的次数。因此,将函数调用为diceroll(k=2,n=1000)应该返回一个类似于:{2:19,3:50,4:82,5:112,6:135,7:174,8:133,9:114,10:75,11:70,12:36}

到目前为止,我已经成功地定义了骰子函数,但我正在努力将k(掷骰数)添加到骰子函数中。到目前为止,我所拥有的:

from numpy import random

def dice():
    return random.randint(1, 7)

def diceroll(number_of_times):
    counter = {n : 0 for n in range(2, 13)}

    for i in range(number_of_times):
        first_dice = dice()
        second_dice = dice()
        total = first_dice + second_dice
        counter[total] += 1
    return counter

diceroll(1000)

输出: {2: 19, 3: 49, 4: 96, 5: 112, 6: 150, 7: 171, 8: 151, 9: 90, 10: 89, 11: 47, 12:26}

如有任何建议,我们将不胜感激

回答后编辑的代码

import random

def diceroll(k, n, dice_sides=6):
    # prepare dictionary with zero values for all possible results
    counter = {n : 0 for n in range(k, k*dice_sides + 1)}

    # roll all the dice
    for i in range(n):
        dice_sum = sum(random.choices(range(1, dice_sides + 1), k = k))
        counter[dice_sum] += 1
    return counter

diceroll(k=2, n=1000)

输出: {2: 20, 3: 49, 4: 91, 5: 116, 6: 140, 7: 138, 8: 173, 9: 112, 10: 72, 11: 65, 12:24}


Tags: 函数inforreturndefcounterrangerandom
3条回答

如果您确实想使用numpy,这将更快,但只有在您有大量掷骰和骰子的情况下才会明显更快:

def diceroll(k, n, dice_sides=6):
    rolls = np.random.randint(dice_sides, size = (k, n)) + 1
    counter = {k:v for k, v in zip(*np.unique(rolls.sum(1), return_counts = True))}
    return counter

diceroll(1000, 2)
Out[]: 
{2: 31,
 3: 49,
 4: 105,
 5: 120,
 6: 136,
 7: 163,
 8: 152,
 9: 109,
 10: 70,
 11: 40,
 12: 25}

您可以使用collectors.counter来跟踪卷。
此外,这可能取决于偏好,但没有理由为random这样简单的东西导入numpy

In [1]: import random

In [2]: from collections import Counter

In [3]: def dice():
   ...:     return random.randint(1,7)
   ...:


In [4]: def dice_roll(number_of_times):
   ...:     counter = Counter()
   ...:     for i in range(number_of_times):
   ...:         first_dice = dice()
   ...:         second_dice = dice()
   ...:         total = first_dice + second_dice
   ...:         counter[total] += 1
   ...:     return counter
   ...:

In [5]: def multiple_rolls(k, number_of_times):
   ...:     final_counter = Counter()
   ...:     for i in range(k):
   ...:         final_counter.update(dice_roll(number_of_times))
   ...:     return final_counter
   ...:

In [6]: multiple_rolls(2, 1000)

Out[6]:
Counter({9: 247,
         5: 170,
         10: 198,
         6: 196,
         8: 251,
         4: 123,
         12: 102,
         7: 249,
         14: 44,
         2: 44,
         11: 184,
         3: 105,
         13: 87})

您可以利用一次提供同一函数的多个卷的随机函数:random.choices(iterable, k=number of results)。这比多次滚动1个骰子并将数值相加要快

您需要将代码更改为:

import random


def diceroll(number_of_dices, number_of_times, dice_sides=6):
    # prepare dictionary with zero values for all possible results
    counter = {n : 0 for n in range(number_of_dices, number_of_dices*dice_sides + 1)}

    # roll all the dice
    for i in range(number_of_times):
        dice_sum = sum(random.choices(range(1, dice_sides + 1), k = number_of_dices))
        counter[dice_sum] += 1

    return counter

print(diceroll(3, 100))

输出:

{ 3:  0,  4: 1,  5: 1,  6: 7,  7: 10,  8: 10,  9: 16, 10: 10, 
 11: 19, 12: 8, 13: 8, 14: 3, 15:  4, 16: 2,  17:  1, 18: 0}

相关问题 更多 >

    热门问题