FFRANK has asked for the wisdom of the Perl Monks concerning the following question:
Need to calculate the probability that the sum of random variables equals some value.
Training set: Number of objects (e.g. arrays of numbers), calculate the frequency that the sum of the object equals 0, 1, 2..max.
Probability: Find the probability that the sum of a number of random variables equals some number (between 0 and max), given those frequencies from the training set.
Example: After sampling (X) objects, the following frequencies have been found from the training set: Freq(sum=0) = 0.1 Freq(sum=1) = 0.2 Freq(sum=2) = 0.7
What is the probability that the sum of 2 elements = 4? This code does the job:
I have much LARGER SUMS to evaluate that derive from larger number of elements (thousands), with MORE FREQUENCIES (up to 10) and doubt that this code will ever scale up well.#!/usr/bin/perl -w use strict; use Algorithm::Loops qw(NestedLoops); use List::Util qw(sum); #Set no. of elements, frequencies and the sum value my $nElements = 2; my @freq = qw (0.1 0.2 0.7); my $targetSum = 4; #Ways of generating sum given no. of elements my @pos = (0..$#freq); my (@combo, @matrix); for my $c (0..$nElements-1) { push @combo, [@pos]; } my @nest = NestedLoops(\@combo, sub { [ @_ ] } ); for my $n (0..$#nest) { push @{$matrix[sum @{$nest[$n]}]}, join ('', @{$nest[$n]}); } my @ways = @{$matrix[$targetSum]}; #Now calculate P-value my @pVal; foreach my $w (0..$#ways) { my @f = split ('', $ways[$w]); #print "@f\n"; my $p = $freq[$f[0]]; #print $p,"\n"; for my $g (1..$#f) { $p *= $freq[$f[$g]]; } push @pVal, $p; } my $pVal = sum @pVal; print "P-value(sum of $nElements = $targetSum) = $pVal\n"; #Prints: P-value(sum of 2 = 4) = 0.49
Is there a module that can be used for this ? Or is there some way to do this that would scale up nicely. Convolutions ? FFT ? I am no mathematician, if you may please provide details.
Thank you very much, best.
FFRANK
|
|---|