Wann sollte ein Argument in Python auf None gesetzt werden?
Der Schwerpunkt meiner Frage liegt auf Design.
Wenn ich ein Argument habe, das sein kann Noneund das zwischen mehreren Funktionen übergeben wird, bis es schließlich verwendet wird, welche Funktion sollte es als Standardargument behandeln?
Angenommen, der folgende Codeblock:
def foo(a):
b = # some code block to assign b
return bar(a, b)
def bar(a, b):
c = # some code block to assign c
return baz(a, b, c)
def baz(a, b, c):
return a + b + c
Der Standardwert sollte nur in festgelegt werden foound alle anderen Funktionen müssen das Argument als obligatorisch erwarten (z. B. foo(a=None); bar(a, b); baz(a, b, c)). Oder gibt es ein besseres Design?
Und wenn eine Typüberprüfung erforderlich war, welche Funktion ist dafür am besten geeignet?
Antworten
Um vernünftige Entscheidungen über Standardargumente treffen zu können, muss man den Kontext kennen, in dem diese Funktionen verwendet werden! .
Wenn fooes Teil der öffentlichen API eines Moduls oder einer Komponente sein soll, wird bei der Angabe eines Standardarguments a=Nonedavon ausgegangen , dass es ein häufiges Verwendungsszenario gibt, in dem foo()in dieser Form ohne Parameter aufgerufen wird. Das gleiche Maß gilt für barund baz:
Werden diese Funktionen nur "intern" verwendet? Dann wissen Sie genau, ob die Angabe eines Standardarguments Ihnen Wiederholungscode erspart oder ob
bar(a, b)es nur ein- oder zweimal aufgerufen wird, möglicherweise nur innerhalbfoo. In diesem Fall ist ein Standardargument nicht vorteilhaftoder sind diese Funktionen auch Teil der öffentlichen API? Dann müssen Sie abschätzen, wie das typische Nutzungsszenario aussehen wird (für das Sie einen realen Kontext benötigen). Wenn Sie die Möglichkeit bereitstellen möchten,
barwie aufgerufen zu werdenbar(b="some value"), ist die Angabe der Signaturbar(a=none, b)erforderlich, unabhängig vom Standardparameter infoo.
Wenn Sie also Entscheidungen über Standardargumente treffen möchten, schauen Sie nicht auf die Implementierungsseite, sondern auf die Verwendungsseite!
In Bezug auf die Typüberprüfung: Ich bin kein Experte für dieses Thema in Python, aber ich denke, wenn Sie Typanmerkungen für die statische Typanalyse hinzufügen möchten, ist es meiner Meinung nach am sinnvollsten, sie auf jeder Ebene der Aufrufkette hinzuzufügen (möglicherweise) tatsächlich obligatorisch, damit die Typanalyse funktioniert). Wenn die "innerste Funktion" ( baz) nur Argumente eines bestimmten Typs erwartet, müssen Sie dort offensichtlich die Typanmerkungen einfügen. Dies impliziert jedoch, dass foound barfunktioniert nur mit Argumenten desselben Typs korrekt, was bedeutet, dass für die statische Typanalyse auch dort die Anmerkungen erforderlich sind.