For the same task, I have coded two different functions. I would like to know which one is more elegant to use.
The task is to check a pydot
object if it beholds a requested node, and if so, to return the node and the graph object back.
If the node doesn't exist, the node needs to be created.
To get the names of the nodes, I use the pydot
objects get_nodes()
function. However, if there aren't any nodes introduced yet, this function returns an empty list. Hence, before iterating over the values, I make an empty list check.
The first variant (’variant1') is easy to understand. After the length check, which is necessary because of node.get_name()
, it loops over to node names and once the node that is being searched for is found, the node and the graph is returned. If not, it calls a function that creates the node and updates the graph. Although this function is easy to understand, IMHO it is not elegant. It beholds two ’return’ statements:
def variant1(node_name, graph):
if len(graph.get_nodes()) > 0:
for node in graph.get_nodes():
if node_name == node.get_name():
return node, graph
return create_node(node_name, graph)
The second variant, is quite more complicated. Once the node is found in the graph, it breaks and jumps directly to the last row (’return node, graph’). This variant has only one return statement.
def variant2(node_name, graph):
if len(graph.get_nodes()) > 0:
for node in graph.get_nodes():
if node_name == node.get_name():
break
else:
# the node doesnt exist. create it and update the graph
node, graph = create_node(node_name, graph)
else:
# create the first node in the graph
node, graph = create_node(node_name, graph)
return node, graph
My question is, which one should I prefer to use, according to the ’The Zen of Python’, ’PEP8’ or ’Google Python Style Guide’?
Here's how I'd write it:
def variant1a(node_name, graph):
"""Include a docstring, too!"""
for node in graph.get_nodes():
if node.get_name() == node_name:
return node, graph
return create_node(node_name, graph)
This means:
create_node
(DRY!);return
lines, both are at the bottom of the function;for: else:
(which some people dislike - I think it's useful in general, but unnecessary here); and len(graph.get_nodes)
is zero the loop is skipped anyway).PEP-8 doesn't prohibit multiple return
lines (indeed, some of the examples in the style guide do have them). I couldn't see a reference to it in Google's style guide, but I didn't expand all of the sections!