sla*_*law 8 python generator python-3.x
我可以访问一个产生两个值的生成器:
def get_document_values():
docs = query_database() # returns a cursor to database documents
for doc in docs:
# doc is a dictionary with ,say, {'x': 1, 'y': 99}
yield doc['x'], doc['y']
Run Code Online (Sandbox Code Playgroud)
我有另一个函数,process_x我无法更改,可以将生成器作为输入来处理x所有文档(如果生成元组,那么它只处理元组的第一个元素并忽略其他元素):
X = process_x(get_document_values()) # This processes x but ignores y
Run Code Online (Sandbox Code Playgroud)
但是,我还需要存储y生成器中的所有值.我唯一的解决方案是执行get_document_values两次:
Y = [y for x,y in get_document_values()] #Throw away x
X = process_x(get_document_values()) #Throw away y
Run Code Online (Sandbox Code Playgroud)
这在技术上有效,但是当有许多文档要处理时,新文档可能会插入到数据库中,并且长度X和Y将会不同.需要在X和之间进行一对一的映射,Y并且我只需要调用get_document_values一次而不是两次.
我考虑过这样的事情:
Y = []
def process_y(doc_generator):
global Y
for x,y in doc_generator:
Y.append(y)
yield x
X = process_x(process_y(get_document_values()))
Run Code Online (Sandbox Code Playgroud)
但:
Y 需要声明为全局变量 我希望有更清洁,更pythonic的方式来做到这一点.
更新
实际上,get_document_values返回值x太大而无法集中存储到内存中,process_x实际上会降低内存需求.因此,无法缓存所有内容x.缓存所有这些y都很好.
调用时您已将所有值缓存到列表中:
all_values = [(x,y) for x,y in get_document_values()] #or list(get_document_values())
Run Code Online (Sandbox Code Playgroud)
您可以使用以下方法获取值的迭代器y:
Y = map(itemgetter(1), all_values)
Run Code Online (Sandbox Code Playgroud)
为了x简单的使用:
X = process_x(map(itemgetter(0), all_values))
Run Code Online (Sandbox Code Playgroud)
另一种选择是分离生成器,例如:
def get_document_values(getter):
docs = query_database() # returns a cursor to database documents
for doc in docs:
# doc is a dictionary with ,say, {'x': 1, 'y': 99}
yield getter(doc)
from operator import itemgetter
X = process_x(get_document_values(itemgetter("x")))
Y = list(get_document_values(itemgetter("y")))
Run Code Online (Sandbox Code Playgroud)
这样你就必须执行两次查询,如果你找到一种执行一次查询并复制游标的方法,那么你也可以将其抽象:
def get_document_values(cursor, getter):
for doc in cursor:
# doc is a dictionary with ,say, {'x': 1, 'y': 99}
yield getter(doc)
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
122 次 |
| 最近记录: |