Можно и без массивчика, но только в том случае, если закон распределения можно описать функцией.08.10.03 10:29 Число просмотров: 1397 Автор: DPP <Dmitry P. Pimenov> Статус: The Elderman
необходимо написать ГСЧ, который бы выдавал числа от 0 до 100 включительно, но случайность их была распределена по неравномерному закону. То есть с 70%-ной случайностью генериловалось число от 0 до 70 и соответственно с 30%-ной случайностью число от 71 до 100. Подскажите, как это реализовать на perl? (Это нужно для игрового автомата)
Наверно наоборот тебе надо от 0 до 70 - 30%, 71 до 100 - 70%06.10.03 15:53 Автор: Killer{R} <Dmitry> Статус: Elderman Отредактировано 06.10.03 16:02 Количество правок: 2
> необходимо написать ГСЧ, который бы выдавал числа от 0 до > 100 включительно, но случайность их была распределена по > неравномерному закону. То есть с 70%-ной случайностью > генериловалось число от 0 до 70 и соответственно с 30%-ной > случайностью число от 71 до 100. Подскажите, как это > реализовать на perl? (Это нужно для игрового автомата)
См. ссылу и поисковики по теме: "гауссовское распределение генерация случайной величины"
Там задаешь нужную дисперсию и мат.ожидание и получаешь то, что надо
> Там задаешь нужную дисперсию и мат.ожидание и получаешь то, > что надо Это было-бы круче чем просто результат разбить на числовой диапазон (0..70) (71..100), но у меня 3 балла по математике:)
ой скока алгоритмов для этого написали. дайте-ка и я ченить напишу Ж)06.10.03 15:41 Автор: Killer{R} <Dmitry> Статус: Elderman
при инициализации проги генерируешь здоровый массив и запускаешь цикл который заполняет его числами приvерно так
int xxx[1000];
int i=n=0;
for(n=0;n<710;n++)
{
xxx[n]=i;i++;
if(i==71)i=0;
}
i=71;
for(n=711;n<1000;n++)
{
xxx[n]=i;i++;
if(i==101)i=71;
}
а затем когда надо вызываешь
int x=xxx[1000];
Выгода такого изврата в скорости random здесь вызывается тока 1 раз а это функция довольно тяжелая - для игрового автомата на перле это думаю будет полезно
Как бы это по-проще.06.10.03 22:11 Автор: DPP <Dmitry P. Pimenov> Статус: The Elderman Отредактировано 06.10.03 22:16 Количество правок: 1
> при инициализации проги генерируешь здоровый массив и > запускаешь цикл который заполняет его числами приvерно так
Объяснить по-проще. Массивчик, действительно, раз так в десять больше надо завести. И заполняем его последовательно примерно так: надо чтобы 1 с вероятностью 0.01 вападала - заносим десять единиц, 2 с вероятностью 0.001 - заносим одну двойку, тройка с вероятностью 0.5 - заносим 500 троек. Вероятность вытаскивания тройки и будет 0.5, потому что отношение количества благоприятных событий (вытаскивание 3, а их 500 штук) к общему количеству 100*10 будет 500/1000 = 0.5. Двойка одна, вероятность 1/1000 = 0.001. Так для любого числа свою вероятность можно задать, заполнив им соответствующее количество ячеек массива.
Массивчик потом перетусовать надо (как колоду карт) и вытащить произвольное.
Можно и не тасовать массив07.10.03 12:41 Автор: amirul <Serge> Статус: The Elderman
> Массивчик потом перетусовать надо (как колоду карт) и > вытащить произвольное. Все равно выбирается рандомом. Какая разница случайный индекс в случайном массиве или случайный индекс в неслучайном.
Тогда можно и сократить массивчик.07.10.03 13:20 Автор: DPP <Dmitry P. Pimenov> Статус: The Elderman
> Все равно выбирается рандомом. Какая разница случайный > индекс в случайном массиве или случайный индекс в > неслучайном. Взять массив из 100 элементов, прописать каждый элемент вероятностью его выпадения, сгенерить нормализованное число в диапазоне от 0 до 1, пробежаться по массиву, вычитая из сгенеренного числа значение элемента массива. Как только число станет меньше нуля или равно нулю - индекс и будет это случайное число с учетом неравномерного распределения вероятности.
Тогда можно и сократить массивчик.07.10.03 14:42 Автор: amirul <Serge> Статус: The Elderman
> Взять массив из 100 элементов, прописать каждый элемент > вероятностью его выпадения, сгенерить нормализованное число > в диапазоне от 0 до 1, пробежаться по массиву, вычитая из > сгенеренного числа значение элемента массива. Как только > число станет меньше нуля или равно нулю - индекс и будет > это случайное число с учетом неравномерного распределения > вероятности. Оно то можно. Но с массивом лучше, если нужна скорость. Индексирование в массиве - одна из самых быстрых операций.
А если скорость не нужно, то лучше с массивами и не заморачиваться. Практически для любого распределения, можно вывести формулу преобразования равномерно распределенной случайной величины в величину, распределенную по данному закону.
А в данном конкретном случае это вообще кусочно линейная функция. Вот только уж очень она близка к обычному равномерному распределению. Так что имхо, лучше вообще не заморачиваться, а пренебречь мизерной неравномерностью.
Можно и без массивчика, но только в том случае, если закон распределения можно описать функцией.08.10.03 10:29 Автор: DPP <Dmitry P. Pimenov> Статус: The Elderman
Берёшь любой «равномерный», как ты выразился, генератор...
И вот, после генерации числа, смотришь, к какому диапазону он относится... И если к тому, в котором вероятность должна быть ниже, пропускаешь это число и генеришь его снова... Вероятность появдения числа в «твоём» диапазоне падает в два раза. Если ещё надо уменьшить вероятность, опять проверяешь диапазон... Как ты думаешь, после пропуска второго числа на сколько уменьшиться вероятность? Правильно, в четыре раза! А потом в восемь и т.п. Тебе насколько надо, а то ты фигню какую-то (ниже) написал ;-)
> необходимо написать ГСЧ, который бы выдавал числа от 0 до > 100 включительно, но случайность их была распределена по > неравномерному закону. То есть с 70%-ной случайностью > генериловалось число от 0 до 70 и соответственно с 30%-ной > случайностью число от 71 до 100. Подскажите, как это > реализовать на perl? (Это нужно для игрового автомата)
[Perl] Если важна та единица, которая была заявлена06.10.03 15:23 Автор: amirul <Serge> Статус: The Elderman
> > неравномерному закону. То есть с 70%-ной > случайностью > > генериловалось число от 0 до 70 и соответственно с > 30%-ной > > случайностью число от 71 до 100. Подскажите, как это > > реализовать на perl? (Это нужно для игрового автомата) то есть не [0;69] и [70;99] а именно [0;70] и [71;100], то самый простой вариант: сначала определить диапазон, а в нем равномерно сгенерить число. То есть генерируем по равномерному закону распределения первое число в диапазоне [0;1)
Если оно меньше 0.7 - генерим равномерно число из диапазона [0;70], иначе - из диапазона [71;100]
[Perl] Генерация случайных чисел06.10.03 14:39 Автор: DPP <Dmitry P. Pimenov> Статус: The Elderman Отредактировано 06.10.03 14:42 Количество правок: 1
> необходимо написать ГСЧ, который бы выдавал числа от 0 до > 100 включительно, но случайность их была распределена по > неравномерному закону. То есть с 70%-ной случайностью > генериловалось число от 0 до 70 и соответственно с 30%-ной > случайностью число от 71 до 100. Подскажите, как это > реализовать на perl? (Это нужно для игрового автомата)
От 0 до 100 включительно 101 число. Если при равномерном распределении число из диапазона от 71 до 100 выпадает с вероятностью 0.30, то из диапазона от 0 до 70 с вероятностью 0.71. Это, я тут немножко бред написал 0.30+0.71 не равняется 1.00, однако не имеет смысла заморачиваться с дробными числами.
Вам, видимо, сама методика нужна. Перл тут не причем. Преобразования на любых языках будут выглядеть сходно.
Игровой автомат на ПЕРЛЕ - прикольно.
И еще: вероятность в процентах не измеряется.
[Perl] Ну а где же тут неравномерность?06.10.03 14:26 Автор: amirul <Serge> Статус: The Elderman
> необходимо написать ГСЧ, который бы выдавал числа от 0 до > 100 включительно, но случайность их была распределена по > неравномерному закону. То есть с 70%-ной случайностью > генериловалось число от 0 до 70 и соответственно с 30%-ной > случайностью число от 71 до 100. Подскажите, как это > реализовать на perl? (Это нужно для игрового автомата)
При равномерном законе распределения с вероятностью 0.7 будут попадаться числа от 0 до 69, и с вероятностью 0.3 - 70-99