Exemple simple argparse voulu: 1 argument, 3 résultats

le documentation pour le module argparse python , bien qu'excellent je suis sûr, est trop pour mon cerveau débutant minuscule pour saisir en ce moment. Je n'ai pas besoin de faire des maths sur la ligne de commande ou de me mêler des lignes de formatage sur l'écran ou de changer les caractères de l'option. Tout ce que je veux faire est "si arg est A, faire ceci, Si B faire cela, si aucun des ci-dessus montrer l'AIDE et quitter" .

425
demandé sur Mr. Xcoder 2011-09-15 11:11:46

9 réponses

ma compréhension de la question originale est double. Tout d'abord, pour ce qui est de l'exemple le plus simple possible d'argparse, je suis surpris de ne pas l'avoir vu ici. Bien sûr, pour être simple, c'est aussi tout au-dessus de nous avec peu de puissance, mais ça pourrait vous aider à démarrer.

import argparse

parser = argparse.ArgumentParser()
parser.add_argument("a")
args = parser.parse_args()

if args.a == 'magic.name':
    print 'You nailed it!'

mais cet argument de position est maintenant nécessaire. Si vous l'omettez lors de l'invocation de ce programme, vous obtiendrez une erreur à propos des arguments manquants. Cela m'amène à la deuxième partie de l' question d'origine. Matt Wilkie semble vouloir un seul argument optionnel sans étiquette nommée (l'option -- labels). Ma suggestion serait de modifier le code ci-dessus comme suit:

...
parser.add_argument("a", nargs='?', default="check_string_for_empty")
...
if args.a == 'check_string_for_empty':
    print 'I can tell that no argument was given and I can deal with that here.'
elif args.a == 'magic.name':
    print 'You nailed it!'
else:
    print args.a

Il pourrait bien y avoir une solution plus élégante, mais cela fonctionne et est minimaliste.

188
répondu mightypile 2014-02-26 15:31:21

Voici comment je le fais avec argparse (avec plusieurs args):

parser = argparse.ArgumentParser(description='Description of your program')
parser.add_argument('-f','--foo', help='Description for foo argument', required=True)
parser.add_argument('-b','--bar', help='Description for bar argument', required=True)
args = vars(parser.parse_args())

args sera un dictionnaire contenant les arguments:

if args['foo'] == 'Hello':
    # code here

if args['bar'] == 'World':
    # code here

Dans votre cas, ajoutez simplement un seul argument.

301
répondu Diego Navarro 2014-06-12 19:26:03

la documentation argparse est raisonnablement bonne mais laisse de côté quelques détails utiles qui pourraient ne pas être évidents. (@Diego Navarro en a déjà mentionné quelques - uns, mais je vais essayer de développer un peu sa réponse.) L'usage de base est le suivant:

parser = argparse.ArgumentParser()
parser.add_argument('-f', '--my-foo', default='foobar')
parser.add_argument('-b', '--bar-value', default=3.14)
args = parser.parse_args()

l'objet que vous récupérez de parse_args() est un objet 'Namespace': un objet dont les variables membres sont nommées d'après vos arguments en ligne de commande. L'objet Namespace est la façon dont vous accédez à votre arguments et les valeurs qui leur sont associées:

args = parser.parse_args()
print args.my_foo
print args.bar_value

(notez que argparse remplace" - " dans vos noms d'arguments par des underscores lorsque vous nommez les variables.)

dans de nombreuses situations, vous pouvez vouloir utiliser des arguments simplement comme des drapeaux qui ne prennent aucune valeur. Vous pouvez ajouter ceux en argparse comme ceci:

parser.add_argument('--foo', action='store_true')
parser.add_argument('--no-foo', action='store_false')

ce qui précède créera des variables nommées 'foo' avec la valeur True, et 'no_foo' avec la valeur False, respectivement:

if (args.foo):
    print "foo is true"

if (args.no_foo is False):
    print "nofoo is false"

Notez aussi que vous pouvez utiliser l'option "required" lorsque vous ajoutez un argument:

parser.add_argument('-o', '--output', required=True)

de cette façon si vous omettez cet argument à la ligne de commande argparse vous dira qu'il est manquant et d'arrêter l'exécution de votre script.

enfin, notez qu'il est possible de créer une structure dict de vos arguments en utilisant la fonction vars , si cela vous facilite la vie.

args = parser.parse_args()
argsdict = vars(args)
print argsdict['my_foo']
print argsdict['bar_value']

comme vous pouvez le voir, vars retourne un dict avec vos noms d'argument comme clés et leurs valeurs comme, er, valeurs.

il y a beaucoup d'autres options et choses que vous pouvez faire, mais cela devrait couvrir les scénarios d'utilisation les plus essentiels et courants.

177
répondu DMH 2011-12-13 17:58:08

Matt pose des questions sur les paramètres de position dans argparse, et je suis d'accord que la documentation Python fait défaut sur cet aspect. Il n'y a pas un seul exemple complet dans les ~20 pages impaires qui montre à la fois parsing et en utilisant les paramètres de position .

Aucune des autres réponses ici montrent un exemple complet de paramètres positionnels, donc voici un exemple complet:

# tested with python 2.7.1
import argparse

parser = argparse.ArgumentParser(description="An argparse example")

parser.add_argument('action', help='The action to take (e.g. install, remove, etc.)')
parser.add_argument('foo-bar', help='Hyphens are cumbersome in positional arguments')

args = parser.parse_args()

if args.action == "install":
    print("You asked for installation")
else:
    print("You asked for something other than installation")

# The following do not work:
# print(args.foo-bar)
# print(args.foo_bar)

# But this works:
print(getattr(args, 'foo-bar'))

La chose qui m'a jeté argparse convertira l'argument nommé "--foo-bar" en "foo_bar", mais un paramètre de position nommé "foo-bar" restera comme "foo-bar", ce qui le rendra moins évident comment l'utiliser dans votre programme.

remarquez les deux lignes près de la fin de mon exemple -- ni l'une ni l'autre ne fonctionneront pour obtenir la valeur du paramètre de position de la barre de foo. Le premier est évidemment faux (c'est une expression arithmétique args.foo minus bar), mais le second ne fonctionne pas non plus:

AttributeError: 'Namespace' object has no attribute 'foo_bar'

si vous voulez utiliser l'attribut foo-bar , vous devez utiliser getattr , comme vu dans la dernière ligne de mon exemple. Ce qui est fou, c'est que si vous essayiez d'utiliser dest=foo_bar pour changer le nom de la propriété en quelque chose qui est plus facile d'accès, vous obtiendriez un message d'erreur vraiment bizarre:

ValueError: dest supplied twice for positional argument

Voici comment l'exemple ci-dessus s'exécute:

$ python test.py
usage: test.py [-h] action foo-bar
test.py: error: too few arguments

$ python test.py -h
usage: test.py [-h] action foo-bar

An argparse example

positional arguments:
  action      The action to take (e.g. install, remove, etc.)
  foo-bar     Hyphens are cumbersome in positional arguments

optional arguments:
  -h, --help  show this help message and exit

$ python test.py install foo
You asked for installation
foo
49
répondu Mark E. Haase 2015-03-03 17:14:32

Notez le tutoriel Argparse dans Python HOWTOs . Il commence à partir de la plupart des exemples de base, comme celui-ci:

import argparse
parser = argparse.ArgumentParser()
parser.add_argument("square", type=int,
                    help="display a square of a given number")
args = parser.parse_args()
print(args.square**2)

et progresse vers les moins basiques.

il y a un exemple avec un choix prédéfini pour une option, comme ce qui est demandé:

import argparse
parser = argparse.ArgumentParser()
parser.add_argument("square", type=int,
                    help="display a square of a given number")
parser.add_argument("-v", "--verbosity", type=int, choices=[0, 1, 2],
                    help="increase output verbosity")
args = parser.parse_args()
answer = args.square**2
if args.verbosity == 2:
    print("the square of {} equals {}".format(args.square, answer))
elif args.verbosity == 1:
    print("{}^2 == {}".format(args.square, answer))
else:
    print(answer)
9
répondu Alexey 2016-03-13 12:27:06

voici ce que j'ai trouvé dans mon projet d'apprentissage grâce principalement à @DMH...

le code de Démonstration:

import argparse

def main():
    parser = argparse.ArgumentParser()
    parser.add_argument('-f', '--flag', action='store_true', default=False)  # can 'store_false' for no-xxx flags
    parser.add_argument('-r', '--reqd', required=True)
    parser.add_argument('-o', '--opt', default='fallback')
    parser.add_argument('arg', nargs='*') # use '+' for 1 or more args (instead of 0 or more)
    parsed = parser.parse_args()
    # NOTE: args with '-' have it replaced with '_'
    print('Result:',  vars(parsed))
    print('parsed.reqd:', parsed.reqd)

if __name__ == "__main__":
    main()

cela peut avoir évolué et est disponible en ligne: command-line.py

Script pour donner à ce code un entraînement: command-line-demo.sh

6
répondu Peter L 2016-06-18 08:55:38

encore une autre introduction sommaire, inspiré par ce post .

import argparse

# define functions, classes, etc.

# executes when your script is called from the command-line
if __name__ == "__main__":

    parser = argparse.ArgumentParser()
    #
    # define each option with: parser.add_argument
    #
    args = parser.parse_args() # automatically looks at sys.argv
    #
    # access results with: args.argumentName
    #

les Arguments sont définis avec les combinaisons des suivantes:

parser.add_argument( 'name', options... )              # positional argument
parser.add_argument( '-x', options... )                # single-char flag
parser.add_argument( '-x', '--long-name', options... ) # flag with long name

les options courantes sont:

  • aide : description pour cet arg lorsque --help est utilisé.
  • par défaut : par défaut valeur si l'argument est omis.
  • type : si vous attendez un float ou int (autrement est str ).
  • dest : donner un nom différent à un drapeau (par exemple '-x', '--long-name', dest='longName' ).

    Note: par défaut --long-name est accessible avec args.long_name
  • action : pour la manipulation spéciale de certains argument
    • store_true, store_false : pour les args booléens

      '--foo', action='store_true' => args.foo == True
    • store_const : à utiliser avec option const

      '--foo', action='store_const', const=42 => args.foo == 42
    • count : pour les options répétées, comme dans ./myscript.py -vv

      '-v', action='count' => args.v == 2
    • append : pour les options répétées, comme dans ./myscript.py --foo 1 --foo 2

      '--foo', action='append' => args.foo == ['1', '2']
  • nécessaire : si un indicateur est requis, ou un de position argument n'est pas.
  • nargs : pour un drapeau à capturer n args

    ./myscript.py --foo a b => args.foo = ['a', 'b']
  • choix pour limiter les entrées possibles (spécifiez comme liste de chaînes, ou ints si type=int ).
5
répondu Sheljohn 2018-03-12 14:43:21

pour ajouter à ce que d'autres ont déclaré:

j'aime généralement utiliser le paramètre 'dest' pour spécifier un nom de variable et ensuite utiliser 'globals().mise à jour()' pour mettre ces variables dans l'espace de noms global.

Utilisation:

$ python script.py -i "Hello, World!"

Code:

...
parser.add_argument('-i', '--input', ..., dest='inputted_variable',...)
globals().update(vars(parser.parse_args()))
...
print(inputted_variable) # Prints "Hello, World!"
2
répondu Sandy Chapman 2013-12-12 13:47:22

vous pouvez également utiliser placette (une enveloppe autour de argparse ).

en bonus, il génère des instructions d'aide soignées - voir ci-dessous.

exemple de script:

#!/usr/bin/env python3
def main(
    arg: ('Argument with two possible values', 'positional', None, None, ['A', 'B'])
):
    """General help for application"""
    if arg == 'A':
        print("Argument has value A")
    elif arg == 'B':
        print("Argument has value B")

if __name__ == '__main__':
    import plac
    plac.call(main)

exemple de sortie:

aucun argument fourni - example.py :

usage: example.py [-h] {A,B}
example.py: error: the following arguments are required: arg

argument inattendu fourni - example.py C :

usage: example.py [-h] {A,B}
example.py: error: argument arg: invalid choice: 'C' (choose from 'A', 'B')

argument Correct fourni - example.py A :

Argument has value A

menu d'aide complet (généré automatiquement) - example.py -h :

usage: example.py [-h] {A,B}

General help for application

positional arguments:
  {A,B}       Argument with two possible values

optional arguments:
  -h, --help  show this help message and exit

Brève Explication:

le nom de l'argument est habituellement égal au nom du paramètre ( arg ).

Le tuple annotation après arg paramètre a la signification suivante:

  • Description ( Argument with two possible values )
  • Type de l'argument de la 'drapeau', 'option' ou 'position' ( positional )
  • Abréviation ( None )
  • Type de la valeur de l'argument - eg. float, string ( None )
  • ensemble Restreint de choix ( ['A', 'B'] )

Documentation:

pour en savoir plus sur l'utilisation de plac consultez sa grande documentation:

Plac: Analyse de la Ligne de Commande le Chemin le plus Facile

2
répondu quasoft 2017-01-30 17:26:02