I have a function that can accept a list of numbers, a tuple of numbers, or s string of numbers and a variable, n, and it creates a list of tuples of length n as it iterates over the passed in iterable.
At this point it works as expected:
numbers = [1, 2, 3, 4, 5, 6]
# numbers = (1, 2, 3, 4, 5, 6)
# numbers = '123456'
def window(iterable, n):
if n == 0:
return []
final = []
last = len(iterable) - (n - 1)
for start in range(0, last):
tup = tuple(numbers[start:start + n])
final.append(tup)
start += 1
return final
print(window(numbers, 2))
print()
print(window(numbers, 3))
print()
print(window(numbers, 4))
Sample outputs from the list and string:
[(1, 2), (2, 3), (3, 4), (4, 5), (5, 6)]
[(1, 2, 3), (2, 3, 4), (3, 4, 5), (4, 5, 6)]
[(1, 2, 3, 4), (2, 3, 4, 5), (3, 4, 5, 6)]
[('1', '2'), ('2', '3'), ('3', '4'), ('4', '5'), ('5', '6')]
[('1', '2', '3'), ('2', '3', '4'), ('3', '4', '5'), ('4', '5', '6')]
[('1', '2', '3', '4'), ('2', '3', '4', '5'), ('3', '4', '5', '6')]
Now I need to allow the function to accept a generator but still generate the same style output.
Ex:
numbers = [1, 2, 3, 4, 5, 6]
squares = (n**2 for n in numbers)
window(squares, 3)
[(1, 4, 9), (4, 9, 16), (9, 16, 25), (16, 25, 36)]
If I run this as is, I get:
TypeError: object of type 'generator' has no len()
I understand why. My issue is that all I can think of is 'dumping' the generator output into a list and then running it through the function, which is lame. It makes no sense to allow a generator as a valid input only to then exhaust it into a list.
I figured out how to identify if a generator is passed in:
import types
def window(iterable, n):
if n == 0:
return []
final = []
if isinstance(iterable, types.GeneratorType):
print('Gen')
else:
last = len(iterable) - (n - 1)
for start in range(0, last):
tup = tuple(numbers[start:start + n])
final.append(tup)
start += 1
return final
But I am stuck as to how to proceed in generating the desired output when a generator is passed in.