# Generator expressions are not useful for extracting matrix colums import copy def plus(v,w): return [x+y for (x,y) in zip(v,w)] def getcol_list(M,j): return [m[j] for m in M] def getcol_gen(M,j): return (m[j] for m in M) def getcol_map(M,j): return map(lambda m: m[j], M) # Define a matrix (list of lists) A = [[i*j for j in range(1,6)] for i in range(1,11)] # Extract column 2 as a list and do stuff with it: OK print("with list:") c = getcol_list(A,2) print(plus([0]*10,c)) print(plus([1]*10,c)) # Again, but with generator expression - does not work print("with generator object:") c = getcol_gen(A,2) print(plus([0]*10,c)) print(plus([1]*10,c)) # Again, but with map - does not work print("with map:") c = getcol_map(A,2) print(plus([0]*10,c)) print(plus([1]*10,c)) # A reusable generator class ReusableGenerator(): def __init__(self,g): self.g = g def __iter__(self): return self.g() print("with a reusable generator:") c = ReusableGenerator(lambda: (a[2] for a in A)) print(plus([0]*10,c)) print(plus([1]*10,c)) # Trying another reusable generator # this does not work, cannot copy a generator object. Why not? class ReusableGenerator2(): def __init__(self,genexp): print("ReusableGenerator got a",genexp) self.g = genexp def __iter__(self): return copy.deepcopy(self.g) # stupid? print("with another reusable generator attempt, it does not work:") c = ReusableGenerator2(a[2] for a in A) print(plus([0]*10,c)) print(plus([1]*10,c)) # Strange error message: # TypeError: zip argument #2 must support iteration # even though __iter__() is defined. # Running it by hand results in a differnt error message: # TypeError: object.__new__(generator) is not safe, use generator.__new__()