TL; DR
Verwenden Sie die nargs
Option oder die 'append'
Einstellung der action
Option (je nachdem, wie sich die Benutzeroberfläche verhalten soll).
Nargs
parser.add_argument('-l','--list', nargs='+', help='<Required> Set flag', required=True)
# Use like:
# python arg.py -l 1234 2345 3456 4567
nargs='+'
nimmt 1 oder mehr Argumente, nargs='*'
nimmt null oder mehr.
anhängen
parser.add_argument('-l','--list', action='append', help='<Required> Set flag', required=True)
# Use like:
# python arg.py -l 1234 -l 2345 -l 3456 -l 4567
Mit append
bieten Sie die Möglichkeit, die Liste mehrmals aufzubauen.
Nicht benutzen type=list
!!! - Es gibt wahrscheinlich keine Situation, in der Sie verwenden möchtentype=list
mit argparse
. Je.
Schauen wir uns einige der verschiedenen Möglichkeiten und das Endergebnis genauer an.
import argparse
parser = argparse.ArgumentParser()
# By default it will fail with multiple arguments.
parser.add_argument('--default')
# Telling the type to be a list will also fail for multiple arguments,
# but give incorrect results for a single argument.
parser.add_argument('--list-type', type=list)
# This will allow you to provide multiple arguments, but you will get
# a list of lists which is not desired.
parser.add_argument('--list-type-nargs', type=list, nargs='+')
# This is the correct way to handle accepting multiple arguments.
# '+' == 1 or more.
# '*' == 0 or more.
# '?' == 0 or 1.
# An int is an explicit number of arguments to accept.
parser.add_argument('--nargs', nargs='+')
# To make the input integers
parser.add_argument('--nargs-int-type', nargs='+', type=int)
# An alternate way to accept multiple inputs, but you must
# provide the flag once per input. Of course, you can use
# type=int here if you want.
parser.add_argument('--append-action', action='append')
# To show the results of the given option to screen.
for _, value in parser.parse_args()._get_kwargs():
if value is not None:
print(value)
Hier ist die Ausgabe, die Sie erwarten können:
$ python arg.py --default 1234 2345 3456 4567
...
arg.py: error: unrecognized arguments: 2345 3456 4567
$ python arg.py --list-type 1234 2345 3456 4567
...
arg.py: error: unrecognized arguments: 2345 3456 4567
$ # Quotes won't help here...
$ python arg.py --list-type "1234 2345 3456 4567"
['1', '2', '3', '4', ' ', '2', '3', '4', '5', ' ', '3', '4', '5', '6', ' ', '4', '5', '6', '7']
$ python arg.py --list-type-nargs 1234 2345 3456 4567
[['1', '2', '3', '4'], ['2', '3', '4', '5'], ['3', '4', '5', '6'], ['4', '5', '6', '7']]
$ python arg.py --nargs 1234 2345 3456 4567
['1234', '2345', '3456', '4567']
$ python arg.py --nargs-int-type 1234 2345 3456 4567
[1234, 2345, 3456, 4567]
$ # Negative numbers are handled perfectly fine out of the box.
$ python arg.py --nargs-int-type -1234 2345 -3456 4567
[-1234, 2345, -3456, 4567]
$ python arg.py --append-action 1234 --append-action 2345 --append-action 3456 --append-action 4567
['1234', '2345', '3456', '4567']
Imbissbuden :
- Verwenden
nargs
oderaction='append'
nargs
kann aus Anwendersicht einfacher sein, aber es kann nicht intuitiv sein, wenn es Positionsargumente gibt, weil argparse
nicht gesagt werden kann, was ein Positionsargument sein soll und was zu dem gehört nargs
; Wenn Sie dann Positionsargumente habenaction='append'
möglicherweise die bessere Wahl.
- Das Obige ist nur wahr, wenn
nargs
gegeben '*'
ist '+'
, oder '?'
. Wenn Sie eine Ganzzahl (z. B. 4
) angeben, gibt es keine Probleme beim Mischen von Optionen mit nargs
und Positionsargumenten, daargparse
genau bekannt ist, wie viele Werte für die Option zu erwarten sind.
- Verwenden Sie keine Anführungszeichen in der Befehlszeile 1
- Nicht benutzen
type=list
, da eine Liste mit Listen zurückgegeben wird
- Dies geschieht, weil unter der Haube
argparse
der Wert von verwendet wird type
, um jedes einzelne gegebene Argument zu erzwingen Ihnen gewähltetype
, nicht das Aggregat aller Argumente.
- Sie können
type=int
(oder was auch immer) verwenden, um eine Liste von Ints (oder was auch immer) zu erhalten.
1 : Ich meine im Allgemeinen nicht. Ich meine, Anführungszeichen zu verwenden, um eine Liste zu übergeben,argparse
ist nicht das, was Sie wollen.
type=list
Option verwenden. Benutze das nicht. Das macht aus einer Zeichenfolge eine Liste und damit die Listen der Listen.type
Parameter auf ein anderes Objekt. Standardmäßig gibt diese Methode eine Liste von Zeichenfolgen zurück.--
könnte Optionen gegen Positionsargumente aufteilen.prog --opt1 par1 ... -- posp1 posp2 ...
--
hilft, dies herauszufinden, wie im Beispiel in meinem vorherigen Kommentar gezeigt. IOW-Benutzer liefert--
gefolgt von allen Positionsargumenten.Ich bevorzuge es, eine begrenzte Zeichenfolge zu übergeben, die ich später im Skript analysiere. Die Gründe dafür sind: die Liste kann von jeder Art sein ,
int
oderstr
, und manchmal mitnargs
mir auf Probleme stoßen , wenn es mehr optionalen Argumente und Positionsargumente sind.Dann,
oder,
wird gut funktionieren. Das Trennzeichen kann auch ein Leerzeichen sein, das jedoch Anführungszeichen um den Argumentwert erzwingt, wie im Beispiel in der Frage.
quelle
type
Argument auflambda s: [int(time) for item in s.split(',')]
anstatt auf Nachbearbeitung setzenargs.list
.int(time)
sollte seinint(item)
. Mein Beispiel war eine vereinfachte Version von dem, was ich normalerweise mache, wo ich viele andere Dinge überprüfe, anstatt eine einfache Verarbeitung. Aber um die Frage einfach zu beantworten, finde ich auch Ihren Weg eleganter ..lambda items: list(csv.reader([items]))[0]
Mit der Standard- CSV- Bibliothek ist eine modifizierte Version des Kommentars von @chepner für alle, die sich Sorgen über willkürliche CSV-Eingaben machen ( siehe Antwort von @adamk ).Zusätzlich
nargs
möchten Sie möglicherweise Folgendes verwenden,choices
wenn Sie die Liste im Voraus kennen:quelle
Verwenden des nargs-Parameters nargs in der Methode add_argument von argparse
Ich benutze nargs = ' ' als add_argument Parameter. Ich habe speziell nargs = 'verwendet ' für die Option auszuwählen, wenn ich keine expliziten Argumente übergebe
Einschließlich eines Code-Snippets als Beispiel:
Beispiel: temp_args1.py
Bitte beachten Sie: Der folgende Beispielcode ist in Python3 geschrieben. Durch Ändern des Druckanweisungsformats kann in python2 ausgeführt werden
Hinweis: Ich sammle mehrere Zeichenfolgenargumente, die in der Liste gespeichert werden - opts.alist Wenn Sie eine Liste von Ganzzahlen wünschen, ändern Sie den Typparameter in parser.add_argument in int
Ausführungsergebnis:
quelle
temp_args1.py -i [item5 ,item6, item7]
und lassen Sie die Ausgabe auch als Liste herauskommen (anstelle der verschachtelten Liste)Wenn Sie beabsichtigen, einen einzelnen Schalter für mehrere Parameter zu verwenden, verwenden Sie
nargs='+'
. Wenn Ihr Beispiel '-l' tatsächlich ganze Zahlen nimmt:Produziert
Wenn Sie dasselbe Argument mehrmals angeben, wird die Standardaktion (
'store'
) die vorhandenen Daten.Die Alternative besteht darin, die folgende
append
Aktion zu verwenden:Welches produziert
Oder Sie können einen benutzerdefinierten Handler / eine benutzerdefinierte Aktion schreiben, um durch Kommas getrennte Werte zu analysieren, damit Sie dies tun können
quelle
In
add_argument()
,type
ist nur ein aufrufbare Objekt , das String und gibt Optionswert erhält.Dies ermöglicht:
quelle
Wenn Sie eine verschachtelte Liste haben, in der die inneren Listen unterschiedliche Typen und Längen haben, und Sie den Typ beibehalten möchten, z.
[[1, 2], ["foo", "bar"], [3.14, "baz", 20]]
Dann können Sie die von @ sam-mason vorgeschlagene Lösung für diese unten gezeigte Frage verwenden :
was gibt:
quelle
Ich möchte mehrere Listen, ganzzahlige Werte und Zeichenfolgen übergeben.
Hilfreicher Link => Wie übergebe ich eine Bash-Variable an Python?
Ordnung ist nicht wichtig. Wenn Sie eine Liste übergeben wollen tun, wie in zwischen
"["
und"]
und trennen sie ein Komma.Dann,
Ausgabe =>
['my_string', '3', ['1', '2'], ['3', '4', '5']]
,my_args
Variable enthält die Argumente der Reihe nach.quelle
Ich denke, die eleganteste Lösung besteht darin, eine Lambda-Funktion an "type" zu übergeben, wie von Chepner erwähnt. Wenn Sie vorher nicht wissen, wie der Begrenzer Ihrer Liste aussehen wird, können Sie außerdem mehrere Begrenzer an re.split übergeben:
quelle
-l
im Beispielaufruf? Woher kam-n
es?parser.add_argument('-l', '--list', type = lambda s: re.split('[ ,;]', s))
. Hier ist die Eingabe :script.py -l abc xyz, abc\nxyz
. Zum Schluss noch das Ergebnis:script.py: error: unrecognized arguments: xyz, abcnxyz