Как рассчитать средневзвешенное значение?


Мой язык - PHP, но алгоритм должен быть достаточно универсальным.

У меня есть ассоциативный массив (скажем так) оценок и количество раз, когда эта оценка была дана.

$ratings = array(
    1 => 1,
    2 => 3,
    3 => 6,
    4 => 3,
    5 => 3
);

Это эквивалентно: [1, 2, 2, 2, 3, 3, 3, 3, 3, 3, 4, 4, 4, 5, 5, 5], но, учитывая числа, с которыми я работаю, было бы довольно неэффективно преобразовывать из первой формы во вторую.

Каким будет алгоритм вычисления среднего значения приведенных выше чисел?

Author: nickf, 2009-01-29

3 answers

Попробуйте это:

$total = 0;
$count = 0;
foreach($ratings as $number=>$frequency) {
  $total += $number * $frequency;
  $count += $frequency;
}
return $total / $count;
 17
Author: Ray Hidayat, 2009-01-29 03:10:44

Разве это не сработало бы?

$total = 0;
$sum = 0;
foreach ($ratings as $k => $v) {
  $total += $k * $v;
  $sum += $v;
}
echo $total / $sum;

РЕДАКТИРОВАТЬ: Ну, я выгляжу глупо, так как кто-то опередил меня в этом. Ну что ж.

 10
Author: Sasha, 2009-01-29 03:13:19

Сомневаюсь, что смогу превзойти принятый ответ, но я нахожу, что встроенные циклические функции работают быстрее, чем циклы сценариев. Не уверен, насколько хорошо будут оптимизированы вызовы $multiply. Если это действительно медленно, то я ожидаю, что кто-нибудь укажет на это в комментарии.

function multiply( $k , $v ) { return $k * $v; }
return array_sum( array_map( 'multiply' , array_keys($ratings) , $ratings ) ) / array_sum( $ratings );
 3
Author: Sparr, 2009-01-29 04:48:06