For the given data, calculate the standard deviation value (sigma).
Standard deviation is a statistical term that shows how compact data distribution is. The formula is the following:

where N is the number of elements in the array x; is the average value (see Task 56, Average on an array).
Let’s use some test data from Wikipedia and take the straightforward approach using reduction operations and avoiding explicit loops:
my @data = 727.7, 1086.5, 1091.0, 1361.3, 1490.5, 1956.1;
my $avg = ([+] @data) / @data.elems;
my $sigma = sqrt(
([+] map * ** 2, map * - $avg, @data) /
(@data.elems - 1)
);
say $sigma; # 420.962489619523
Inside the sqrt
function, the [+]
reduction operator gets the array that is formed by the two nested runs of map
. First, the constant shift has been removed by applying * - $avg
to each element. Second, a square of each item has been calculated:Â * ** 2
.
In both cases, the WhateverCode
is used. It is usually more expressive but may lead to constructs like * ** 2
, which look a bit cryptic.
The two map
s can be merged into one:
my $sigma = sqrt(
([+] map (* - $avg) ** 2, @data) / (@data.elems - 1)
);
Now, let’s explore the second approach that gets the same result using feed operators. In Perl 6, there are feed operators of both directions: <==
and ==>
. Their shape indicates the direction of data flow, so here is another version of the program.
my @data = 727.7, 1086.5, 1091.0, 1361.3, 1490.5, 1956.1;
my $avg = ([+] @data) / @data.elems;
@data
==> map * - $avg
==> map * ** 2
==> reduce * + *
==> my @σ;
say sqrt(@σ[0] / (@data.elems - 1)); # 420.962489619523
The data flow is clearly visible now. The @data
array passes the two map
s, and then, it is reduced using the +
operation. The call of reduce * + *
is equivalent to using the reduction operator in the form of [+]
.
Notice how the @σ
array is defined, not only the fact that a Unicode name is used but mostly the fact that the my
declaration is placed at the end of the feed chain. An array is used here because the feed operator does not return a scalar value, although we only need one element.
To make the code even closer to the original mathematical formula, you may choose a different name for the variable holding the average value (and remove the elemscall):
my $x̄= ([+] @data) / @data;