Skip to content

Commit 5ff012a

Browse files
authored
Better presentation order for recipes. (gh-116755)
1 parent e54bdea commit 5ff012a

File tree

1 file changed

+43
-43
lines changed

1 file changed

+43
-43
lines changed

Doc/library/itertools.rst

Lines changed: 43 additions & 43 deletions
Original file line numberDiff line numberDiff line change
@@ -785,8 +785,8 @@ well as with the built-in itertools such as ``map()``, ``filter()``,
785785

786786
A secondary purpose of the recipes is to serve as an incubator. The
787787
``accumulate()``, ``compress()``, and ``pairwise()`` itertools started out as
788-
recipes. Currently, the ``sliding_window()`` and ``iter_index()`` recipes
789-
are being tested to see whether they prove their worth.
788+
recipes. Currently, the ``sliding_window()``, ``iter_index()``, and ``sieve()``
789+
recipes are being tested to see whether they prove their worth.
790790

791791
Substantially all of these recipes and many, many others can be installed from
792792
the `more-itertools project <https://pypi.org/project/more-itertools/>`_ found
@@ -795,12 +795,12 @@ on the Python Package Index::
795795
python -m pip install more-itertools
796796

797797
Many of the recipes offer the same high performance as the underlying toolset.
798-
Superior memory performance is kept by processing elements one at a time
799-
rather than bringing the whole iterable into memory all at once. Code volume is
800-
kept small by linking the tools together in a functional style which helps
801-
eliminate temporary variables. High speed is retained by preferring
802-
"vectorized" building blocks over the use of for-loops and :term:`generator`\s
803-
which incur interpreter overhead.
798+
Superior memory performance is kept by processing elements one at a time rather
799+
than bringing the whole iterable into memory all at once. Code volume is kept
800+
small by linking the tools together in a `functional style
801+
<https://www.cs.kent.ac.uk/people/staff/dat/miranda/whyfp90.pdf>`_. High speed
802+
is retained by preferring "vectorized" building blocks over the use of for-loops
803+
and :term:`generators <generator>` which incur interpreter overhead.
804804

805805
.. testcode::
806806

@@ -873,6 +873,14 @@ which incur interpreter overhead.
873873
"Returns True if all the elements are equal to each other."
874874
return len(take(2, groupby(iterable, key))) <= 1
875875

876+
def unique_justseen(iterable, key=None):
877+
"List unique elements, preserving order. Remember only the element just seen."
878+
# unique_justseen('AAAABBBCCDAABBB') --> A B C D A B
879+
# unique_justseen('ABBcCAD', str.casefold) --> A B c A D
880+
if key is None:
881+
return map(operator.itemgetter(0), groupby(iterable))
882+
return map(next, map(operator.itemgetter(1), groupby(iterable, key)))
883+
876884
def unique_everseen(iterable, key=None):
877885
"List unique elements, preserving order. Remember all elements ever seen."
878886
# unique_everseen('AAAABBBCCDAABBB') --> A B C D
@@ -889,35 +897,6 @@ which incur interpreter overhead.
889897
seen.add(k)
890898
yield element
891899

892-
def unique_justseen(iterable, key=None):
893-
"List unique elements, preserving order. Remember only the element just seen."
894-
# unique_justseen('AAAABBBCCDAABBB') --> A B C D A B
895-
# unique_justseen('ABBcCAD', str.casefold) --> A B c A D
896-
if key is None:
897-
return map(operator.itemgetter(0), groupby(iterable))
898-
return map(next, map(operator.itemgetter(1), groupby(iterable, key)))
899-
900-
def iter_index(iterable, value, start=0, stop=None):
901-
"Return indices where a value occurs in a sequence or iterable."
902-
# iter_index('AABCADEAF', 'A') --> 0 1 4 7
903-
seq_index = getattr(iterable, 'index', None)
904-
if seq_index is None:
905-
# Path for general iterables
906-
it = islice(iterable, start, stop)
907-
for i, element in enumerate(it, start):
908-
if element is value or element == value:
909-
yield i
910-
else:
911-
# Path for sequences with an index() method
912-
stop = len(iterable) if stop is None else stop
913-
i = start
914-
try:
915-
while True:
916-
yield (i := seq_index(value, i, stop))
917-
i += 1
918-
except ValueError:
919-
pass
920-
921900
def sliding_window(iterable, n):
922901
"Collect data into overlapping fixed-length chunks or blocks."
923902
# sliding_window('ABCDEFG', 4) --> ABCD BCDE CDEF DEFG
@@ -967,6 +946,27 @@ which incur interpreter overhead.
967946
slices = starmap(slice, combinations(range(len(seq) + 1), 2))
968947
return map(operator.getitem, repeat(seq), slices)
969948

949+
def iter_index(iterable, value, start=0, stop=None):
950+
"Return indices where a value occurs in a sequence or iterable."
951+
# iter_index('AABCADEAF', 'A') --> 0 1 4 7
952+
seq_index = getattr(iterable, 'index', None)
953+
if seq_index is None:
954+
# Path for general iterables
955+
it = islice(iterable, start, stop)
956+
for i, element in enumerate(it, start):
957+
if element is value or element == value:
958+
yield i
959+
else:
960+
# Path for sequences with an index() method
961+
stop = len(iterable) if stop is None else stop
962+
i = start
963+
try:
964+
while True:
965+
yield (i := seq_index(value, i, stop))
966+
i += 1
967+
except ValueError:
968+
pass
969+
970970
def iter_except(func, exception, first=None):
971971
""" Call a function repeatedly until an exception is raised.
972972

@@ -1047,8 +1047,8 @@ The following recipes have a more mathematical flavor:
10471047

10481048
Computes with better numeric stability than Horner's method.
10491049
"""
1050-
# Evaluate x³ -4x² -17x + 60 at x = 2.5
1051-
# polynomial_eval([1, -4, -17, 60], x=2.5) --> 8.125
1050+
# Evaluate x³ -4x² -17x + 60 at x = 5
1051+
# polynomial_eval([1, -4, -17, 60], x=5) --> 0
10521052
n = len(coefficients)
10531053
if not n:
10541054
return type(x)(0)
@@ -1311,10 +1311,10 @@ The following recipes have a more mathematical flavor:
13111311

13121312
>>> from fractions import Fraction
13131313
>>> from decimal import Decimal
1314-
>>> polynomial_eval([1, -4, -17, 60], x=2)
1315-
18
1316-
>>> x = 2; x**3 - 4*x**2 -17*x + 60
1317-
18
1314+
>>> polynomial_eval([1, -4, -17, 60], x=5)
1315+
0
1316+
>>> x = 5; x**3 - 4*x**2 -17*x + 60
1317+
0
13181318
>>> polynomial_eval([1, -4, -17, 60], x=2.5)
13191319
8.125
13201320
>>> x = 2.5; x**3 - 4*x**2 -17*x + 60

0 commit comments

Comments
 (0)