Improve grouper() recipe to demonstrate all forms of zip() (GH-30837)

This commit is contained in:
Raymond Hettinger 2022-01-23 14:31:10 -06:00 committed by GitHub
parent f7955a82e3
commit 270a09184d
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
2 changed files with 41 additions and 9 deletions

View file

@ -813,11 +813,20 @@ which incur interpreter overhead.
return starmap(func, repeat(args))
return starmap(func, repeat(args, times))
def grouper(iterable, n, fillvalue=None):
def grouper(iterable, n, *, incomplete='fill', fillvalue=None):
"Collect data into non-overlapping fixed-length chunks or blocks"
# grouper('ABCDEFG', 3, 'x') --> ABC DEF Gxx
# grouper('ABCDEFG', 3, fillvalue='x') --> ABC DEF Gxx
# grouper('ABCDEFG', 3, incomplete='strict') --> ABC DEF ValueError
# grouper('ABCDEFG', 3, incomplete='ignore') --> ABC DEF
args = [iter(iterable)] * n
if incomplete == 'fill':
return zip_longest(*args, fillvalue=fillvalue)
if incomplete == 'strict':
return zip(*args, strict=True)
if incomplete == 'ignore':
return zip(*args)
else:
raise ValueError('Expected fill, strict, or ignore')
def triplewise(iterable):
"Return overlapping triplets from an iterable"

View file

@ -2436,6 +2436,21 @@ Samuele
... else:
... return starmap(func, repeat(args, times))
>>> def grouper(iterable, n, *, incomplete='fill', fillvalue=None):
... "Collect data into non-overlapping fixed-length chunks or blocks"
... # grouper('ABCDEFG', 3, fillvalue='x') --> ABC DEF Gxx
... # grouper('ABCDEFG', 3, incomplete='strict') --> ABC DEF ValueError
... # grouper('ABCDEFG', 3, incomplete='ignore') --> ABC DEF
... args = [iter(iterable)] * n
... if incomplete == 'fill':
... return zip_longest(*args, fillvalue=fillvalue)
... if incomplete == 'strict':
... return zip(*args, strict=True)
... if incomplete == 'ignore':
... return zip(*args)
... else:
... raise ValueError('Expected fill, strict, or ignore')
>>> def triplewise(iterable):
... "Return overlapping triplets from an iterable"
... # pairwise('ABCDEFG') -> ABC BCD CDE DEF EFG
@ -2453,11 +2468,6 @@ Samuele
... window.append(x)
... yield tuple(window)
>>> def grouper(n, iterable, fillvalue=None):
... "grouper(3, 'ABCDEFG', 'x') --> ABC DEF Gxx"
... args = [iter(iterable)] * n
... return zip_longest(*args, fillvalue=fillvalue)
>>> def roundrobin(*iterables):
... "roundrobin('ABC', 'D', 'EF') --> A D E B F C"
... # Recipe credited to George Sakkis
@ -2626,9 +2636,22 @@ True
>>> dotproduct([1,2,3], [4,5,6])
32
>>> list(grouper(3, 'abcdefg', 'x'))
>>> list(grouper('abcdefg', 3, fillvalue='x'))
[('a', 'b', 'c'), ('d', 'e', 'f'), ('g', 'x', 'x')]
>>> it = grouper('abcdefg', 3, incomplete='strict')
>>> next(it)
('a', 'b', 'c')
>>> next(it)
('d', 'e', 'f')
>>> next(it)
Traceback (most recent call last):
...
ValueError: zip() argument 2 is shorter than argument 1
>>> list(grouper('abcdefg', n=3, incomplete='ignore'))
[('a', 'b', 'c'), ('d', 'e', 'f')]
>>> list(triplewise('ABCDEFG'))
[('A', 'B', 'C'), ('B', 'C', 'D'), ('C', 'D', 'E'), ('D', 'E', 'F'), ('E', 'F', 'G')]