Странное поведение с rand () - PullRequest
       0

Странное поведение с rand ()

0 голосов
/ 29 декабря 2010

Почему условие rand ()% 3 верно приблизительно КАЖДЫЙ 3 раза?Рэнд действительно случайно, не так ли?

Ответы [ 3 ]

3 голосов
/ 29 декабря 2010

Вы понимаете, конечно, что даже честная монета может дать вам десять голов подряд.Эту комбинацию можно присвоить вероятности.

Справедливая монета даст половину головы и полхвоста за много испытаний, но она не гарантированно будет 50/50 за более короткий пробег,

Ваш собственный опыт физического мира говорит вам, что ваш вывод неверен.То же самое верно для rand ().

1 голос
/ 29 декабря 2010

Как сказано в справочной странице Linux для rand():

Однако в более старых реализациях rand () и в текущих реализациях в разных системах биты младшего разряда намного менее случайны, чем биты старшего разряда. Не используйте эту функцию в приложениях, предназначенных для переноса, когда необходима хорошая случайность.

Таким образом, вы можете захотеть использовать другой генератор случайных чисел или вытянуть биты более высокого порядка (которые могут демонстрировать большую случайность).

Типичная реализация rand() представляет собой линейный конгруэнтный генератор , который представляет собой не что иное, как умножение и сложение некоторых чисел со специальными свойствами (относительная простота). Например, пара реализаций:

  • MSVC 2010 rand():

     return( ((ptd->_holdrand = ptd->_holdrand * 214013L
                + 2531011L) >> 16) & 0x7fff );
    
  • rand() из рабочей среды IAR:

     (x) * 1664525L + 1013904223L           
    

Вы заметите, что rand() в MSVC 2010 сдвигает результат вправо, я полагаю, чтобы помочь с проблемой, описанной в справочной странице Linux о неслучайности в младших битах.

Однако, если вы хотите улучшить случайность своих результатов, вы можете захотеть использовать подпрограмму, основанную на чем-то вроде Mersenne twister , для которой реализации легко доступны в Интернете.

0 голосов
/ 11 мая 2016

У меня была такая же проблема с этим кодом:

#include<iostream.h>
#include<stdlib.h>
int main()
{
    srand(NULL);       
    cout << rand() % 10 + 1;
}

После 10 раз его выполнения я получал 1 каждый раз.Но я изменил начальное число следующим образом:

#include<iostream.h>
#include<stdlib.h>
//new include:
#include<time.h>
int main()
{
    srand(time(NULL));       
    cout << rand() % 10 + 1;
}

Это потому, что RANDOMIZER берет начальное значение (srand ()), которое в первом случае оказывается пустым, затем запускает заданный алгоритм,Выход 1. Если основание семени вовремя, таким образом получая «случайный» результат.Надеюсь, это поможет.

...