https://github.com/python/cpython/commit/2afba5ca6d27c69bc0a1618e86c2e4c00eefa4c1
commit: 2afba5ca6d27c69bc0a1618e86c2e4c00eefa4c1
branch: main
author: Raymond Hettinger <[email protected]>
committer: rhettinger <[email protected]>
date: 2024-09-09T20:57:49-05:00
summary:

Small improvements to the itertools docs (GH-123885)

files:
M Doc/library/itertools.rst
M Lib/test/test_itertools.py

diff --git a/Doc/library/itertools.rst b/Doc/library/itertools.rst
index 553abf788b223a..508c20f4df6f5e 100644
--- a/Doc/library/itertools.rst
+++ b/Doc/library/itertools.rst
@@ -474,7 +474,7 @@ loops that truncate the stream.
    If *start* is zero or ``None``, iteration starts at zero.  Otherwise,
    elements from the iterable are skipped until *start* is reached.
 
-   If *stop* is ``None``, iteration continues until the iterator is
+   If *stop* is ``None``, iteration continues until the iterable is
    exhausted, if at all.  Otherwise, it stops at the specified position.
 
    If *step* is ``None``, the step defaults to one.  Elements are returned
@@ -503,6 +503,10 @@ loops that truncate the stream.
                   yield element
                   next_i += step
 
+   If the input is an iterator, then fully consuming the *islice*
+   advances the input iterator by ``max(start, stop)`` steps regardless
+   of the *step* value.
+
 
 .. function:: pairwise(iterable)
 
@@ -601,6 +605,8 @@ loops that truncate the stream.
            # product('ABCD', 'xy') → Ax Ay Bx By Cx Cy Dx Dy
            # product(range(2), repeat=3) → 000 001 010 011 100 101 110 111
 
+           if repeat < 0:
+               raise ValueError('repeat argument cannot be negative')
            pools = [tuple(pool) for pool in iterables] * repeat
 
            result = [[]]
@@ -684,6 +690,8 @@ loops that truncate the stream.
    Roughly equivalent to::
 
         def tee(iterable, n=2):
+            if n < 0:
+                raise ValueError('n must be >= 0')
             iterator = iter(iterable)
             shared_link = [None, None]
             return tuple(_tee(iterator, shared_link) for _ in range(n))
@@ -703,6 +711,12 @@ loops that truncate the stream.
    used anywhere else; otherwise, the *iterable* could get advanced without
    the tee objects being informed.
 
+   When the input *iterable* is already a tee iterator object, all
+   members of the return tuple are constructed as if they had been
+   produced by the upstream :func:`tee` call.  This "flattening step"
+   allows nested :func:`tee` calls to share the same underlying data
+   chain and to have a single update step rather than a chain of calls.
+
    ``tee`` iterators are not threadsafe. A :exc:`RuntimeError` may be
    raised when simultaneously using iterators returned by the same :func:`tee`
    call, even if the original *iterable* is threadsafe.
diff --git a/Lib/test/test_itertools.py b/Lib/test/test_itertools.py
index 9c0c4b4de18cf1..6820dce3f12620 100644
--- a/Lib/test/test_itertools.py
+++ b/Lib/test/test_itertools.py
@@ -992,12 +992,16 @@ def product1(*args, **kwds):
                 else:
                     return
 
-        def product2(*args, **kwds):
+        def product2(*iterables, repeat=1):
             'Pure python version used in docs'
-            pools = list(map(tuple, args)) * kwds.get('repeat', 1)
+            if repeat < 0:
+                raise ValueError('repeat argument cannot be negative')
+            pools = [tuple(pool) for pool in iterables] * repeat
+
             result = [[]]
             for pool in pools:
                 result = [x+[y] for x in result for y in pool]
+
             for prod in result:
                 yield tuple(prod)
 
@@ -1754,6 +1758,8 @@ def test_tee_recipe(self):
         # Begin tee() recipe ###########################################
 
         def tee(iterable, n=2):
+            if n < 0:
+                raise ValueError('n must be >= 0')
             iterator = iter(iterable)
             shared_link = [None, None]
             return tuple(_tee(iterator, shared_link) for _ in range(n))
@@ -1829,11 +1835,9 @@ def _tee(iterator, link):
         self.assertEqual(list(a), list(range(100,2000)))
         self.assertEqual(list(c), list(range(2,2000)))
 
-        # Tests not applicable to the tee() recipe
-        if False:
-            # test invalid values of n
-            self.assertRaises(TypeError, tee, 'abc', 'invalid')
-            self.assertRaises(ValueError, tee, [], -1)
+        # test invalid values of n
+        self.assertRaises(TypeError, tee, 'abc', 'invalid')
+        self.assertRaises(ValueError, tee, [], -1)
 
         for n in range(5):
             result = tee('abc', n)

_______________________________________________
Python-checkins mailing list -- [email protected]
To unsubscribe send an email to [email protected]
https://mail.python.org/mailman3/lists/python-checkins.python.org/
Member address: [email protected]

Reply via email to