字典叶生成器
Dictionary leaf generator
这是我的树,一个嵌套的字典
tree = {"root": {"branch_a": {"branch_aa": 0, "branch_ab": 1},
"branch_b": 1,
"branch_c": {"branch_ca": {"branch_caa": 0}}}}
我设法编写了一个打印所有叶子的函数
def print_leaves(tree):
if not hasattr(tree, "__iter__"):
print(tree)
elif isinstance(tree, dict):
for branch in tree.values():
print_leaves(branch)
产生所需的输出
0
1
1
0
在这一点上,我认为将操作(在本例中为打印)与对叶子的访问分离会很好。所以我稍微修改了上面的函数,把它变成了一个生成器,并将打印部分移动到一个for循环中。
def generate_leaves(tree):
if not hasattr(tree, "__iter__"):
yield tree
elif isinstance(tree, dict):
for branch in tree.values():
generate_leaves(branch)
for leaf in generate_leaves(tree):
print(leaf)
...不幸的是,这不起作用。
首先,为什么它不起作用?
然后,当然,如何正确编写叶生成器?
您没有使用递归调用的结果。这适用于没有 return 值的 print_leaves
,但不适用于具有 return
或 yield
.
的函数
这里是长版:
def generate_leaves(tree):
if not hasattr(tree, "__iter__"):
yield tree
elif isinstance(tree, dict):
for branch in tree.values():
for leaf in generate_leaves(branch):
yield leaf
for leaf in generate_leaves(tree):
print(leaf)
幸运的是,我们可以使用 yield from
:
来缩短很多
def generate_leaves(tree):
if not hasattr(tree, "__iter__"):
yield tree
elif isinstance(tree, dict):
for branch in tree.values():
yield from generate_leaves(branch)
for leaf in generate_leaves(tree):
print(leaf)
请注意,您只需要 if / else
满足一个条件;不需要具有两个冗余条件的 if / elif
:
def generate_leaves(tree):
if not isinstance(tree, dict):
yield tree
else:
for branch in tree.values():
yield from generate_leaves(branch)
for leaf in generate_leaves(tree):
print(leaf)
关于 yield from
的资源:
- PEP-0380;
- In practice, what are the main uses for the new "yield from" syntax in Python 3.3?
这是我的树,一个嵌套的字典
tree = {"root": {"branch_a": {"branch_aa": 0, "branch_ab": 1},
"branch_b": 1,
"branch_c": {"branch_ca": {"branch_caa": 0}}}}
我设法编写了一个打印所有叶子的函数
def print_leaves(tree):
if not hasattr(tree, "__iter__"):
print(tree)
elif isinstance(tree, dict):
for branch in tree.values():
print_leaves(branch)
产生所需的输出
0
1
1
0
在这一点上,我认为将操作(在本例中为打印)与对叶子的访问分离会很好。所以我稍微修改了上面的函数,把它变成了一个生成器,并将打印部分移动到一个for循环中。
def generate_leaves(tree):
if not hasattr(tree, "__iter__"):
yield tree
elif isinstance(tree, dict):
for branch in tree.values():
generate_leaves(branch)
for leaf in generate_leaves(tree):
print(leaf)
...不幸的是,这不起作用。
首先,为什么它不起作用? 然后,当然,如何正确编写叶生成器?
您没有使用递归调用的结果。这适用于没有 return 值的 print_leaves
,但不适用于具有 return
或 yield
.
这里是长版:
def generate_leaves(tree):
if not hasattr(tree, "__iter__"):
yield tree
elif isinstance(tree, dict):
for branch in tree.values():
for leaf in generate_leaves(branch):
yield leaf
for leaf in generate_leaves(tree):
print(leaf)
幸运的是,我们可以使用 yield from
:
def generate_leaves(tree):
if not hasattr(tree, "__iter__"):
yield tree
elif isinstance(tree, dict):
for branch in tree.values():
yield from generate_leaves(branch)
for leaf in generate_leaves(tree):
print(leaf)
请注意,您只需要 if / else
满足一个条件;不需要具有两个冗余条件的 if / elif
:
def generate_leaves(tree):
if not isinstance(tree, dict):
yield tree
else:
for branch in tree.values():
yield from generate_leaves(branch)
for leaf in generate_leaves(tree):
print(leaf)
关于 yield from
的资源:
- PEP-0380;
- In practice, what are the main uses for the new "yield from" syntax in Python 3.3?