I am working in Mathematica. I have a table of 200 elements. I want to calculate the mean value for the first 20 elements, for the second 20 elements and so on, up to 200. I will get a table (matrix) of 10 elements. How I can solve this problem? Thanks for helping.
4 Answers
As Öskå notes you can Partition
your data and then Map
Mean
:
a = {q, r, s, t, u, v, w, x, y};
Mean /@ Partition[a, 3]
{1/3 (q + r + s), 1/3 (t + u + v), 1/3 (w + x + y)}
However if performance is a concern I propose using Total
or Dot
:
blockAverage1[a_List, n_Integer] := a ~Partition~ n ~Total~ {2} / n
blockAverage2[a_List, n_Integer] := Partition[a, n].ConstantArray[1/n, n]
Timings:
a = RandomReal[9, 5*^7]; (* big list *)
Mean /@ Partition[a, 20] // Timing // First
blockAverage1[a, 20] // Timing // First
blockAverage2[a, 20] // Timing // First
1.311 0.0654 0.0306
If you want averages of overlapping blocks see also:
Related:
In versions 10.2+ there is BlockMap
:
a = {q, r, s, t, u, v, w, x, y};
BlockMap[Mean, a, 3]
{1/3 (q + r + s), 1/3 (t + u + v), 1/3 (w + x + y)}
Although this is much slower than the alternatives in Mr.Wizard's answer, its elegance may be of value since OP says
I have a table of 200 elements
Also, an undocumented 6-argument form of Partition
:
Partition[a, 3, 3, None, {}, Mean[{##}] &]
{1/3 (q + r + s), 1/3 (t + u + v), 1/3 (w + x + y)}
list = {q, r, s, t, u, v, w, x, y};
Using SequenceCases
(new in 10.1)
SequenceCases[list, x : {_, _, _} :> Mean @ x]
{(q + r + s)/3, (t + u + v)/3, (w + x + y)/3}
Generalization
SequenceCases[list, x : {Repeated[_, {2}]} :> Mean @ x]
{(q + r)/2, (s + t)/2, (u + v)/2, (w + x)/2}
Using SubsetCases
:
list = {q, r, s, t, u, v, w, x, y};
SubsetCases[list, s : {_, _, _} :> Mean@s]
(*{1/3 (q + r + s), 1/3 (t + u + v), 1/3 (w + x + y)}*)
Or using SequenceSplit
:
SequenceSplit[list, s : {_, _, _} :> Mean@s]
(*{1/3 (q + r + s), 1/3 (t + u + v), 1/3 (w + x + y)}*)
Mean /@ Partition[data, 20]
$\endgroup$