Вероятности
От: SBoyko  
Дата: 15.12.03 06:34
Оценка:
Просьба не пинать
Подскажите пример реализации функции, которая (к примеру) с вероятностью 1/10 будет выдавать 1, 1/15 — 2, и. т.д. Как то вообще ничего путного в голову не лезет
Re: Вероятности
От: SBoyko  
Дата: 15.12.03 07:00
Оценка:
Вот кстати одна из реализаций.


function S(Limit: Integer): Boolean;
begin
   Result := (Random(Limit) = 0);
end;

function RND: Integer;
var
   R : Integer;
begin
   Result:=0;
   if S(10) then Result := 1
      else if S(15) then Result := 2
         else if S(20) then Result := 3;
end;


Как вам?

Результаты работы:

Re: Вероятности
От: mrhru Россия  
Дата: 15.12.03 07:25
Оценка:
Здравствуйте, SBoyko, Вы писали:

SB>Просьба не пинать

SB>Подскажите пример реализации функции, которая (к примеру) с вероятностью 1/10 будет выдавать 1, 1/15 — 2, и. т.д. Как то вообще ничего путного в голову не лезет

1) Завести массив, в котором 1/10 всех элементов содержит 1, 1/15 — 2 и т.д. Получать значение — это выбирать с равномерной вероятностью из массива.

2) Завести список интервалов — структур
double начало_интервала
double конец_интервала
int значение

Разница конец_интервала — начало_интервала должна давать требуемую вероятность.
И естественно, все интервалы должны покрывать [0, 1].
Получать значение — это генерировать с равномерной вероятностью в диапазоне [0, 1] с поиском соответствующего интервала.
Re: Вероятности
От: Кодт Россия  
Дата: 15.12.03 09:50
Оценка: 2 (1)
Здравствуйте, SBoyko, Вы писали:

SB>Подскажите пример реализации функции, которая (к примеру) с вероятностью 1/10 будет выдавать 1, 1/15 — 2, и. т.д. Как то вообще ничего путного в голову не лезет


Типичное решение.

Пусть для конечного или счетного множества X есть распределение вероятности p(x).
Введем над X отношение строгого порядка. Проще говоря, раздадим элементам номера.
Соответственно, p(k) = p(x[k]).
Теперь определим кумулятивную вероятность P(n), означающую вероятность того, что k<=n.
Она равна P(n)=p(0)+p(1)+...+p(n).
Очевидно, что P(n_min-1) = 0, P(n_max)=1. Если последнее неверно, то либо распределение неправильно задано, либо его нужно нормировать (поделить каждое значение p(k) на фактическую сумму, т.е. P(n_max)).

Теперь возьмем случайную величину q, равномерно распределенную на [0;1]. Найдем n(q) : P(n-1)<q<=P(n).
Поскольку длина отрезка [P(n-1);P(n)] по определению равна P(n)-P(n-1)=p(n), то полученная случайная величина n распределена по закону p(n).

Практическое решение:
double frand() { return double(rand())/RAND_MAX; }

int my_random_value_v1()
{
  double q = frand();
  if(q <= 1./10) return 1;
  else if(q <= 1./10 + 1./15) return 2;
  else if(q <= 1./10 + 1./15 + 1./20) return 3;
  else return 4;
}

int my_random_value_v2()
{
  const n = 3;
  struct PX { int x; double p; } px[n+1] = {
    { 1, 1./10 }, { 2, 1./15 }, { 3, 1./20 }, { 4, 0 } // последнее - дефолтное
  };

  double q = frand();
  for(int i = 0; i < n; ++i)
  {
    q -= px[i].p;
    if(q <= 0) break;
  }
  // либо i<n и q0<=(p[0]+...+p[i]), либо i=n+1
  return px[i].x;
}
Перекуём баги на фичи!
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.