Python argparse ignore les arguments non reconnus


206

Optparse, l'ancienne version ignore simplement tous les arguments non reconnus et continue. Dans la plupart des situations, ce n'est pas idéal et a été changé dans argparse. Mais il y a quelques situations où vous souhaitez ignorer tous les arguments non reconnus et analyser ceux que vous avez spécifiés.

Par exemple:

parser = argparse.ArgumentParser()
parser.add_argument('--foo', dest="foo")
parser.parse_args()

$python myscript.py --foo 1 --bar 2
error: unrecognized arguments: --bar

Y a-t-il un moyen de remplacer cela?


14
Très pratique si vous écrivez un wrapper dans un autre programme et que vous souhaitez capturer et modifier quelques arguments, mais passez le reste!
— Alan De Smet

2
Exactement pourquoi je me suis retrouvé ici @AlanDeSmet! Heureux que je
— n'essaye

Réponses:


351

Remplacer

args = parser.parse_args()

avec

args, unknown = parser.parse_known_args()

Par exemple,

import argparse
parser = argparse.ArgumentParser()
parser.add_argument('--foo')
args, unknown = parser.parse_known_args(['--foo', 'BAR', 'spam'])
print(args)
# Namespace(foo='BAR')
print(unknown)
# ['spam']

21
+1 - ne savait pas qu'il y avait quelque chose commeparse_known_args
— avasal

7
Moi non plus! Je l'ai même manqué dans les documents docs.python.org/library/… . Merci
— joedborg

1
Cela est apparu lorsque j'essayais d'utiliser nosetest avec des parseargs (il refusait d'autoriser l'utilisation des arguments nosetest) parce que je le faisais parser.parse_args(None)plutôt que parser.parse_args([])dans mes tests.
— Andy Hayden du

3
FWIW, utiliser parse_known_argsplutôt qu'autoriser parse_argsl'utilisation de ArgumentParsercode dans le cadre de if __name__ == 'main':(une condition qui Trueconcerne toutes les cellules d'un bloc-notes IPython ... que je trouve très utile pour le développement et le test du code que je souhaite éventuellement migrer vers un script appelé à partir d'une ligne de commande)
— gumption

1
Cela ne semble pas fonctionner avec des arguments optionnels "connus" qui ne sont pas transmis.
— Sharud

21

Vous pouvez mettre les parties restantes dans un nouvel argument parser.add_argument('args', nargs=argparse.REMAINDER)si vous souhaitez les utiliser.


1
Cela fonctionne avec parse_args()et ne nécessite pas parse_known_args()(sur Python 2.7).
— OozeMeister

4
L'utilisation d'argparse.REMAINDER semble être lourde de bogues de longue date. Je ne peux certainement pas le faire fonctionner. parse_known_args () est une bonne alternative.
— Matt

1
Je viens de rencontrer un bug REMAINDER de longue date aujourd'hui: bugs.python.org/issue17050
— Scott Carpenter

7

En fait, argparse "ignore" toujours _unrecognized_args. Tant que ces arguments "non reconnus" n'utilisent pas le préfixe par défaut vous n'entendrez aucune plainte de l'analyseur.

En utilisant la configuration de @ anutbu mais avec la norme parse.parse_args(), si nous devions exécuter notre programme avec les arguments suivants.

$ program --foo BAR a b +cd e

Nous aurons cette collection de données à espace de noms avec laquelle travailler.

Namespace(_unrecognized_args=['a', 'b', '+cd', 'e'], foo='BAR')

Si nous voulions que le préfixe par défaut soit -ignoré, nous pourrions changer le ArgumentParser et décider que nous allons utiliser un +pour nos arguments "reconnus" à la place.

parser = argparse.ArgumentParser(prefix_chars='+')
parser.add_argument('+cd')

La même commande produira

Namespace(_unrecognized_args=['--foo', 'BAR', 'a', 'b'], cd='e')

Mettez ça dans votre pipe et fumez-le =)

nJoy!

En utilisant notre site, vous reconnaissez avoir lu et compris notre politique liée aux cookies et notre politique de confidentialité.
Licensed under cc by-sa 3.0 with attribution required.