
14.12.2020, 16:02
|
Новичок на форуме
|
|
Регистрация: 14.12.2020
Сообщений: 3
|
|
Рандом с вероятносью, хелп пж
Допустим есть функцию randomChanses(map)
Т.е. на входе у нас словарь, в котором ключ-символ, а значение-вероятность появление этого символа. Т.е. допустим есть такой набор:
{'a'=10,'b'=20,'c'=30}. Т.е. появление a 1к10, b 1к20, с 1к30. Помогите накидать функцию, которое бы возвращала рандомное значение, учитываю вероятность. Была идея просто создать список, в который поместить 'a' 10 раз, 'b' 20 раз и т.д. Но это не совсем то, да и если шансы будут 1к1000, то слишком долго будет создаваться список.
|
|

14.12.2020, 16:44
|
 |
Профессор
|
|
Регистрация: 25.10.2016
Сообщений: 1,012
|
|
Сообщение от LimonDK
|
{'a'=10,'b'=20,'c'=30}
|
что означают эти числа?
Сообщение от LimonDK
|
функцию, которое бы возвращала рандомное значение
|
значения как должны выглядеть?
в общем, поподробнее бы условие.
Последний раз редактировалось Alexandroppolus, 14.12.2020 в 16:46.
|
|

14.12.2020, 16:49
|
 |
Профессор
|
|
Регистрация: 27.05.2010
Сообщений: 33,136
|
|
LimonDK,
const fun = n => n < 0.16 ? 'a' : n < .5 ? 'b' : 'c';
alert(fun(Math.random()));
|
|

14.12.2020, 16:53
|
 |
Профессор
|
|
Регистрация: 03.02.2020
Сообщений: 2,757
|
|
рони,
Сообщение от LimonDK
|
.е. появление a 1к10, b 1к20, с 1к30.
|
Как это понимать?
30 раз запустили.
В среднем должно быть 1 раз с, 1.5 раза b, 3 раза а. Разве не так?
|
|

14.12.2020, 17:19
|
 |
Профессор
|
|
Регистрация: 27.05.2010
Сообщений: 33,136
|
|
voraa,
Сообщение от LimonDK
|
Была идея просто создать список, в который поместить 'a' 10 раз, 'b' 20 раз и т.д
|
<script>
const fun = n => n < 0.16 ? 'a' : n < .5 ? 'b' : 'c';
const obj = {};
for (let i = 0; i < 60; i++) {
let key = fun(Math.random());
obj[key] = 1 + (obj[key] >> 0);
}
document.write(JSON.stringify(obj, "", 4))
</script>
Последний раз редактировалось рони, 14.12.2020 в 17:23.
|
|

14.12.2020, 17:20
|
 |
Профессор
|
|
Регистрация: 25.10.2016
Сообщений: 1,012
|
|
Сообщение от LimonDK
|
Была идея просто создать список, в который поместить 'a' 10 раз, 'b' 20 раз и т.д.
|
кажется, понял.
потом из этого списка равновероятно выбираем элемент, и он оказывается одним из символов.
это как-раз то, что рони сделал. В общем виде примерно так:
function rnd(map) {
const keys = Object.keys(map);
if (!keys.length) {
return undefined;
}
const sum = keys.reduce((s, key) => s + map[key], 0);
const r = Math.random() * sum;
let acc = 0;
for (let i = 0; i < keys.length; ++i) {
acc += map[keys[i]];
if (acc > r) {
return keys[i];
}
}
return keys[keys.length - 1];
}
// для проверки рандомности
function getStat(map, iters) {
const stat = Object.create(null);
Object.keys(map).forEach(key => { stat[key] = 0; });
for (let i = 0; i < iters; ++i) {
const v = rnd(map);
stat[v]++;
}
Object.keys(map).forEach(key => { stat[key] = stat[key] / iters; });
return stat;
}
alert(JSON.stringify(getStat({'a': 10,'b': 20,'c': 30}, 40000), '', 4));
|
|

14.12.2020, 17:37
|
Новичок на форуме
|
|
Регистрация: 14.12.2020
Сообщений: 3
|
|
Сообщение от voraa
|
рони,
Как это понимать?
30 раз запустили.
В среднем должно быть 1 раз с, 1.5 раза b, 3 раза а. Разве не так?
|
Вот такое хотелось сделать, только не особо понимаю, как каждый раз определять вероятности.
|
|

14.12.2020, 18:23
|
 |
Профессор
|
|
Регистрация: 25.10.2016
Сообщений: 1,012
|
|
то есть вероятности - это на самом деле обратные значения от тех, что в словаре?
гарантируется, что сумма этих обратных значений всегда не больше 1 ?
|
|

14.12.2020, 18:40
|
 |
Профессор
|
|
Регистрация: 27.05.2010
Сообщений: 33,136
|
|
Сообщение от LimonDK
|
Вот такое хотелось сделать, только не особо понимаю, как каждый раз определять вероятности.
|
a : 10, b : 20, с : 30
находим сумму всех весов 10 + 20 + 30 = 60//порядок не имеет значения
первый if 10 * 1/60
второй if (10 + 20) * 1/60
else всё остальное
итого
if(n < 0.16) return 'a';
else if(n < .5) return 'b';
else return 'c'
для примера другой порядок с : 30 , a : 10, b : 20
30 * 1/60
(30 + 10) * 1/60
if(n < .5) return 'c';
else if(n < .66) return 'a';
else return 'b'
|
|

14.12.2020, 18:51
|
 |
Профессор
|
|
Регистрация: 03.02.2020
Сообщений: 2,757
|
|
Тогда с таким же успехом можно было написать
{a:1, b: 2: c:3}
Никакой разницы.
Но между 1/2 и 1/20 для b все таки есть разница.
|
|
|
|