Как получить случайное число в N-ном деапазоне ? - страница 3

 

Alexey Navoykov

интересная мысль, нкогда не задумывался об этом.

 
А вообще, с какой целью сделали rand(), а больше всего интересует почему диапазон от 1 до 32767 из каких критериев исходили.
 
Aleksey Rodionov:
А вообще, с какой целью сделали rand(), а больше всего интересует почему диапазон от 1 до 32767 из каких критериев исходили.

и у вас тоже в работе больше 32767 тс?)

 
Fast528:

и у вас тоже в работе больше 32767 тс?)

Нет =), я не для торговли эксперт делаю, а так мне порядком 1 - ~ 500 случайных чисел нужно.
 
Alexey Navoykov:
Смотрю многие делают одну и ту же ошибку: используют оператор взятия остатка %.  Такое допустимо лишь в том случае, когда исходный диапазон случайных чисел кратен делителю.  Т.е. нашем случае такими делителями являются двойки в различных степенях:  2, 4, 8 и т.д.  Так вот только для них можно писать такое:  rand()%8.
Для любых других делителей вы получите перекос вероятности. Поэтому там нужно делать через вычисление вещественного остатка:  floor(fmod(rand(), 100)) - получаем число от 0 до 99

Не понял. О каком перекосе речь? Оператор "%" возвращает целочисленный остаток от целочисленного деления.

int max =10;
            
for(int c =0; c < 30; c++)
{
int mod =c;
                
        while(mod >= max) // вычисление % вручную
                mod -=max;

        printf("Result - %%: %i mod: %i", (c % max), mod);
}

Возможные "перекосы" могут быть связаны только с качеством алгоритма ГПСЧ.

Поэтому, лучше использовать (если это важно) реальный ГСЧ и быть спокойным за энтропию, матожидание, распределение и прчее

 
SemenTalonov:

Не понял. О каком перекосе речь? Оператор "%" возвращает целочисленный остаток от целочисленного деления.

Возможные "перекосы" могут быть связаны только с качеством алгоритма ГПСЧ.

Поэтому, лучше использовать (если это важно) реальный ГСЧ и быть спокойным за энтропию, матожидание, распределение и прчее

Нужно упростить и листок бумаги. Представить 3 битный генератор с выхлопом от 0 до 7 и вероятностью 1/8, наивную попытку rand()%3. 0,1,2,0,1,2,0,1, вероятность двойки 2/8, а у других вариантов 3/8.

Ещё есть мнение, что качество некоторых ГПСЧ оставляет желать лучшего и младшие разряды могут иметь 010101010101,  что не сильно похоже на случайность.

 
pavlick_:

Нужно упростить и листок бумаги. Представить 3 битный генератор с выхлопом от 0 до 7 и вероятностью 1/8, наивную попытку rand()%3. 0,1,2,0,1,2,0,1, вероятность двойки 2/8, а у других вариантов 3/8.

Ещё есть мнение, что качество некоторых ГПСЧ оставляет желать лучшего и младшие разряды могут иметь 010101010101,  что не сильно похоже на случайность.

Мешает некратный заданному диапазону "хвост"? Его можно просто исключить повторным запуском генератора.

int max =10; // нельзя указать больше MAX_RND (цикл бросков зависнет)
int rnd;

#define MAX_RND 32767 // макс. возможное число генератора
#define MAX_VALID_RND (MAX_RND - (MAX_RND % max)) // верхняя граница кратности диапазону пользователя
   
while((rnd =rand()) > MAX_VALID_RND); // бросаем монету пока выпадают числа в некратном хвосте дипазона генератора
rnd %=max; // приводим в дипазон пользователя от 0 до (max - 1) включительно

Тогда распределение случайностей и в диапазоне пользователя будет честным генераторным, т.е. будет определяться только качеством ГПСЧ.

 
SemenTalonov:

Реально случайное число в диапазоне 0 - 4294967295.

Генерируется побитно на основе счетчика тактов процессора. Работает и на Intel и на AMD, в том числе на новых поколениях.

Компилировать в Microsoft Visual Studio. Как уложить результат в заданный диапазон уже написали


Такой вариант мне больше всего нравится, он самый случайный. А из мт5 или мт4 это можно реализовать? И интересно, как реализована функция rand в мт5, может знает кто или разрабы ответят.
 
Maxim Romanov:
Такой вариант мне больше всего нравится, он самый случайный. А из мт5 или мт4 это можно реализовать? И интересно, как реализована функция rand в мт5, может знает кто или разрабы ответят.

Скомпилировать длл-ку в MVS. Положить её в папку терминала:

C:\Users\User\AppData\Roaming\MetaQuotes\Terminal\...\MQL5\Libraries

Импортировать функцию библиотеки в MQL

#import "realrand.dll"
    uint realrand();
#import
библиотека и код 32-разрядные, терминал тоже должен быть х32
Файлы:
realrand.zip  15 kb
 
SemenTalonov:

Мешает некратный заданному диапазону "хвост"? Его можно просто исключить повторным запуском генератора.

Тогда распределение случайностей и в диапазоне пользователя будет честным генераторным, т.е. будет определяться только качеством ГПСЧ.

На основе чего вы решили что распределение будет честным?  Математические обоснования есть?  У меня лично большие сомнения в этом, чисто интуитивно.  Когда что-то исключаешь, то результат никак не может быть честным, ибо ты вносишь некую ЗАКОНОМЕРНОСТЬ в процесс генерации.

Причина обращения: