@@ -845,7 +845,8 @@ and :term:`generators <generator>` which incur interpreter overhead.
845845 from contextlib import suppress
846846 from functools import reduce
847847 from math import comb, isqrt, prod, sumprod
848- from operator import getitem, is_not, itemgetter, mul, neg
848+ from operator import getitem, is_not, itemgetter, mul, neg, truediv
849+
849850
850851 # ==== Basic one liners ====
851852
@@ -858,9 +859,10 @@ and :term:`generators <generator>` which incur interpreter overhead.
858859 # prepend(1, [2, 3, 4]) → 1 2 3 4
859860 return chain([value], iterable)
860861
861- def tabulate(function, start=0):
862- "Return function(0), function(1), ..."
863- return map(function, count(start))
862+ def running_mean(iterable):
863+ "Yield the average of all values seen so far."
864+ # running_mean([8.5, 9.5, 7.5, 6.5]) -> 8.5 9.0 8.5 8.0
865+ return map(truediv, accumulate(iterable), count(1))
864866
865867 def repeatfunc(function, times=None, *args):
866868 "Repeat calls to a function with specified arguments."
@@ -913,6 +915,7 @@ and :term:`generators <generator>` which incur interpreter overhead.
913915 # all_equal('4٤௪౪໔', key=int) → True
914916 return len(take(2, groupby(iterable, key))) <= 1
915917
918+
916919 # ==== Data pipelines ====
917920
918921 def unique_justseen(iterable, key=None):
@@ -1021,6 +1024,7 @@ and :term:`generators <generator>` which incur interpreter overhead.
10211024 while True:
10221025 yield function()
10231026
1027+
10241028 # ==== Mathematical operations ====
10251029
10261030 def multinomial(*counts):
@@ -1040,6 +1044,7 @@ and :term:`generators <generator>` which incur interpreter overhead.
10401044 # sum_of_squares([10, 20, 30]) → 1400
10411045 return sumprod(*tee(iterable))
10421046
1047+
10431048 # ==== Matrix operations ====
10441049
10451050 def reshape(matrix, columns):
@@ -1058,6 +1063,7 @@ and :term:`generators <generator>` which incur interpreter overhead.
10581063 n = len(m2[0])
10591064 return batched(starmap(sumprod, product(m1, transpose(m2))), n)
10601065
1066+
10611067 # ==== Polynomial arithmetic ====
10621068
10631069 def convolve(signal, kernel):
@@ -1114,6 +1120,7 @@ and :term:`generators <generator>` which incur interpreter overhead.
11141120 powers = reversed(range(1, n))
11151121 return list(map(mul, coefficients, powers))
11161122
1123+
11171124 # ==== Number theory ====
11181125
11191126 def sieve(n):
@@ -1230,8 +1237,8 @@ and :term:`generators <generator>` which incur interpreter overhead.
12301237 [(0, 'a'), (1, 'b'), (2, 'c')]
12311238
12321239
1233- >>> list (islice(tabulate( lambda x : 2 * x), 4 ))
1234- [0, 2, 4, 6 ]
1240+ >>> list (running_mean([ 8.5 , 9.5 , 7.5 , 6.5 ] ))
1241+ [8.5, 9.0, 8.5, 8.0 ]
12351242
12361243
12371244 >>> for _ in loops(5 ):
@@ -1798,6 +1805,10 @@ and :term:`generators <generator>` which incur interpreter overhead.
17981805
17991806 # Old recipes and their tests which are guaranteed to continue to work.
18001807
1808+ def tabulate(function, start=0):
1809+ "Return function(0), function(1), ..."
1810+ return map(function, count(start))
1811+
18011812 def old_sumprod_recipe(vec1, vec2):
18021813 "Compute a sum of products."
18031814 return sum(starmap(operator.mul, zip(vec1, vec2, strict=True)))
@@ -1877,6 +1888,10 @@ and :term:`generators <generator>` which incur interpreter overhead.
18771888.. doctest ::
18781889 :hide:
18791890
1891+ >>> list (islice(tabulate(lambda x : 2 * x), 4 ))
1892+ [0, 2, 4, 6]
1893+
1894+
18801895 >>> dotproduct([1 ,2 ,3 ], [4 ,5 ,6 ])
18811896 32
18821897
0 commit comments