Wie unterscheiden sich "Schlüsselwortargumente" von regulären Argumenten? Können nicht alle Argumente als name=value
anstelle der Positionssyntax übergeben werden?
Wie unterscheiden sich "Schlüsselwortargumente" von regulären Argumenten? Können nicht alle Argumente als name=value
anstelle der Positionssyntax übergeben werden?
Antworten:
Es gibt zwei verwandte Konzepte, die beide als " Schlüsselwortargumente " bezeichnet werden.
Auf der aufrufenden Seite, wie andere Kommentatoren erwähnt haben, können Sie einige Funktionsargumente nach Namen angeben. Sie müssen sie nach allen Argumenten ohne Namen ( Positionsargumente ) erwähnen , und es müssen Standardwerte für alle Parameter vorhanden sein, die überhaupt nicht erwähnt wurden.
Das andere Konzept ist auf der Seite der Funktionsdefinition: Sie können eine Funktion definieren, die Parameter nach Namen nimmt - und Sie müssen nicht einmal angeben, wie diese Namen lauten. Dies sind reine Schlüsselwortargumente und können nicht positionell übergeben werden. Die Syntax lautet
def my_function(arg1, arg2, **kwargs)
Alle Schlüsselwortargumente, die Sie an diese Funktion übergeben, werden in ein Wörterbuch mit dem Namen eingefügt kwargs
. Sie können die Schlüssel dieses Wörterbuchs zur Laufzeit folgendermaßen untersuchen:
def my_function(**kwargs):
print str(kwargs)
my_function(a=12, b="abc")
{'a': 12, 'b': 'abc'}
kwargs
oder kann ich ihn in etw umbenennen? wie options
( def my_fuction(arg1, arg2, **options)
)?
kwargs
ist aber die Konvention, wenn es keinen passenderen Namen gibt
Es gibt ein letztes Sprachmerkmal, bei dem die Unterscheidung wichtig ist. Betrachten Sie die folgende Funktion:
def foo(*positional, **keywords):
print "Positional:", positional
print "Keywords:", keywords
Das *positional
Argument speichert alle an übergebenen Positionsargumente foo()
, ohne die Anzahl der von Ihnen angegebenen zu begrenzen.
>>> foo('one', 'two', 'three')
Positional: ('one', 'two', 'three')
Keywords: {}
Das **keywords
Argument speichert alle Schlüsselwortargumente:
>>> foo(a='one', b='two', c='three')
Positional: ()
Keywords: {'a': 'one', 'c': 'three', 'b': 'two'}
Und natürlich können Sie beide gleichzeitig verwenden:
>>> foo('one','two',c='three',d='four')
Positional: ('one', 'two')
Keywords: {'c': 'three', 'd': 'four'}
Diese Funktionen werden selten verwendet, sind jedoch gelegentlich sehr nützlich, und es ist wichtig zu wissen, welche Argumente Positions- oder Schlüsselwörter sind.
*positional
und **keywords
wenn wir die Funktionsdefinition wie ändern def foo(arg1, *positional, **keywords):
. Hier arg1
ist positionell und erforderlich. Bitte beachten Sie, dass die Position in der Antwort eine optionale und variable Anzahl von Positionsargumenten bedeutet.
foo(bar=True)
, können Sie die Werte mit bar = keywords.pop('bar')
denselben wie erhalten bar = keywords.pop('bar', None)
. Verwenden Sie als Standardwertbar = keywords.pop('bar', False)
Die Verwendung von Schlüsselwortargumenten ist dasselbe wie normale Argumente, außer dass die Reihenfolge keine Rolle spielt. Zum Beispiel sind die beiden folgenden Funktionsaufrufe gleich:
def foo(bar, baz):
pass
foo(1, 2)
foo(baz=2, bar=1)
Sie haben keine Schlüsselwörter vor sich. Die Reihenfolge ist wichtig!
func(1,2,3, "foo")
Sie haben Schlüsselwörter in der Front. Sie können in beliebiger Reihenfolge sein!
func(foo="bar", baz=5, hello=123)
func(baz=5, foo="bar", hello=123)
Sie sollten auch wissen, dass die Reihenfolge wichtig ist, wenn Sie Standardargumente verwenden und das Einfügen der Schlüsselwörter vernachlässigen!
def func(foo=1, baz=2, hello=3): ...
func("bar", 5, 123)
func("bar", 5)
? Und dann sagen, das hello
bekommt seinen Standardwert von 3
.
Es gibt zwei Möglichkeiten, Funktionsparametern Argumentwerte zuzuweisen. Beide werden verwendet.
Nach Position. Positionsargumente haben keine Schlüsselwörter und werden zuerst zugewiesen.
Nach Stichwort. Schlüsselwortargumente haben Schlüsselwörter und werden nach Positionsargumenten an zweiter Stelle zugewiesen.
Beachten Sie, dass Sie die Option haben, Positionsargumente zu verwenden.
Wenn Sie keine Positionsargumente verwenden, stellt sich heraus, dass alles , was Sie geschrieben haben, ein Schlüsselwortargument ist.
Wenn Sie eine Funktion aufrufen, entscheiden Sie sich für die Verwendung von Position, Schlüsselwort oder einer Mischung. Sie können alle Schlüsselwörter auswählen, wenn Sie möchten. Einige von uns treffen diese Wahl nicht und verwenden Positionsargumente.
Ich bin überrascht, dass niemand darauf hingewiesen zu haben scheint, dass man ein Wörterbuch mit Parametern mit Schlüsselargumenten übergeben kann, die die formalen Parameter erfüllen.
>>> def func(a='a', b='b', c='c', **kwargs):
... print 'a:%s, b:%s, c:%s' % (a, b, c)
...
>>> func()
a:a, b:b, c:c
>>> func(**{'a' : 'z', 'b':'q', 'c':'v'})
a:z, b:q, c:v
>>>
, **kwargs
. Dies würde zeigen, dass sogar eine einfache func def mit einer festen Anzahl von Parametern ein Wörterbuch liefern kann. Das heißt, es erfordert nichts Besonderes in der Definition. DANN können Sie ein zweites Beispiel hinzufügen, WITH ** kwargs in der Definition, und zeigen, wie EXTRA-Elemente im Wörterbuch darüber verfügbar sind.
print 'a:%s, b:%s, c:%s' % (a, b, c)
gibt es Syntaxfehler, print('a:%s, b:%s, c:%s' % (a, b, c))
funktioniert aber. Etwas mit Python-Version? Trotzdem danke für diesen Einblick, bis jetzt habe ich den print('a:{}, b:{}, c:{}'.format(a, b, c))
Mit 3 Python Sie können beide erforderlich und nicht erforderlich Schlüsselwort Argumente :
Optional : (Standardwert für Parameter 'b' definiert)
def func1(a, *, b=42):
...
func1(value_for_a) # b is optional and will default to 42
Erforderlich (kein Standardwert für Parameter 'b' definiert):
def func2(a, *, b):
...
func2(value_for_a, b=21) # b is set to 21 by the function call
func2(value_for_a) # ERROR: missing 1 required keyword-only argument: 'b'`
Dies kann in Fällen hilfreich sein, in denen viele ähnliche Argumente nebeneinander stehen, insbesondere wenn sie vom gleichen Typ sind. In diesem Fall bevorzuge ich die Verwendung benannter Argumente oder erstelle eine benutzerdefinierte Klasse, wenn Argumente zusammengehören.
Ich bin überrascht, dass niemand die Tatsache erwähnt hat, dass Sie Positions- und Schlüsselwortargumente mischen können, um hinterhältige Dinge wie diese mit *args
und **kwargs
( von dieser Site ) zu tun :
def test_var_kwargs(farg, **kwargs):
print "formal arg:", farg
for key in kwargs:
print "another keyword arg: %s: %s" % (key, kwargs[key])
Auf diese Weise können Sie beliebige Schlüsselwortargumente verwenden, die möglicherweise Schlüssel enthalten, die Sie nicht im Voraus definieren möchten.
Ich suchte nach einem Beispiel mit Standard-Warns mithilfe von Typanmerkungen:
def test_var_kwarg(a: str, b: str='B', c: str='', **kwargs) -> str:
return ' '.join([a, b, c, str(kwargs)])
Beispiel:
>>> print(test_var_kwarg('A', c='okay'))
A B okay {}
>>> d = {'f': 'F', 'g': 'G'}
>>> print(test_var_kwarg('a', c='c', b='b', **d))
a b c {'f': 'F', 'g': 'G'}
>>> print(test_var_kwarg('a', 'b', 'c'))
a b c {}
Fügen Sie einfach eine Möglichkeit zum Definieren des Standardwerts von Argumenten hinzu, die beim Aufrufen der Funktion nicht in Schlüsselwörtern zugewiesen werden:
def func(**keywargs):
if 'my_word' not in keywargs:
word = 'default_msg'
else:
word = keywargs['my_word']
return word
Nennen Sie dies durch:
print(func())
print(func(my_word='love'))
Du wirst kriegen:
default_msg
love
Lesen Sie mehr über *args
und **kwargs
in Python: https://www.digitalocean.com/community/tutorials/how-to-use-args-and-kwargs-in-python-3