#python #statistics #montecarlo
Вопрос:
Я провел эксперимент, в ходе которого получил 6 различных порядков размера, и теперь пытаюсь понять, значимы ли мои наблюдения. Я должен выполнить моделирование MC, чтобы получить значение p, чтобы увидеть, являются ли мои наблюдаемые значения необычно большими или малыми по сравнению с нулем.
Мне необходимо:
- Настройте схему, в которой порядок 1 равен от 0 до 1/6, Порядок 2 равен от 1/6 до 2/6, порядок 3 равен от 2/6 до 3/6
- Сгенерируйте 20 случайных чисел в диапазоне от 0 до 1 и распределите их по этим ячейкам. Если число, если —
У меня должно быть 6 новых чисел, по одному для каждой ячейки, которые в сумме дают 20, но мой вывод говорит 0. Я новичок в python, так что же я делаю не так?
Мой код здесь:
from random import randint
from random import seed
# seed random number generator
seed(1)
counter = 0
chi_sq_values = []
# want 10,000 simulations
while counter < 10000:
# will eventually mimic your real six orders of size
sim_orders = [0, 0, 0, 0, 0, 0]
# generating 20 random numbers
for i in range(20):
numbers = randint(0, 1)
if 0 <= numbers <= 1 / 6:
numbers = sim_orders[0]
if 1 / 6 <= numbers <= 2 / 6:
numbers = sim_orders[1]
if 2 / 6 <= numbers <= 3 / 6:
numbers = sim_orders[2]
if 3 / 6 <= numbers <= 4 / 6:
numbers = sim_orders[3]
if 4 / 6 <= numbers <= 5 / 6:
numbers = sim_orders[4]
if 5 / 6 <= numbers <= 6 / 6:
numbers = sim_orders[5]
print(sim_orders)
Комментарии:
1. В этом коде довольно много ошибок.
counter = 1
не написано, иsim_orders = [0, 0, 0, 0, 0, 0]
все они равны 0, и вы никогда не меняете их значение, так как этоprint(sim_orders)
даст что-нибудь, кроме[0,0,0,0,0,0]
Ответ №1:
Вы не увеличиваете значения в sim_orders
. Вы добавляете значение в sim_orders
numbers
, что не имеет никакого эффекта, потому что значение всегда 0
. И тогда вы ничего не делаете с numbers
тем, что вы добавляете к нему.
Вам следует увеличить соответствующий счетчик sim_orders
.
Вам нужно использовать random.random()
, а не random.randint(0, 1)
. Последнее просто вернет 0
или 1
, а не число между 0 и 1.
for i in range(20):
numbers = random.random()
if numbers <= 1 / 6:
sim_orders[0] = 1
elif numbers <= 2 / 6:
sim_orders[1] = 1
elif numbers <= 3 / 6:
sim_orders[2] = 1
elif numbers <= 4 / 6:
sim_orders[3] = 1
elif numbers <= 5 / 6:
sim_orders[4] = 1
else:
sim_orders[5] = 1
Вы также должны использовать elif
последовательность взаимоисключающих условий, чтобы избежать ненужных тестов. И если вы сделаете это, вам не нужно проверять оба конца диапазона, так как предыдущий тест исключает числа ниже нижней части диапазона.
Ваши условия перекрывались-если numbers
бы было точное число 1/6
, оно было бы помещено в обе ячейки.
Вы также можете полностью избавиться от всех if
утверждений:
sim_orders[floor(numbers*6)] = 1
Комментарии:
1. Я попробовал это, но это только добавление чисел в позиции [0] и [5] sim_orders. Точка зрения элифа хороша, спасибо!
2. Потому что ты использовал
randint
вместоrandom
3. Ах, спасибо: это странно, потому что онлайн-гид посоветовал мне использовать randint! Еще один вопрос: как заставить мой код перестать выполняться, как только он достигнет 10 000 симуляций? В настоящее время это продолжается вечно
4. Ты никогда не увеличиваешься
counter
. Воспользуйсяfor counter in range(10000):
5. Вы уверены, что в онлайн-руководстве было показано, как генерировать числа от 0 до 1?
Ответ №2:
Если вы не хотите обновлять свой список sim_orders нулями, вам следует исключить его из цикла while. Более того, я не вижу, где вы обновляете свой список сгенерированными номерами. И если вы хотите, чтобы ваш цикл while был конечным, вам нужно увеличить счетчик внутри тела цикла.