2013-06-18 13 views
5

Come definisco una stringa arbitraria come argomento facoltativo usando argparse?python - Usando argparse, passa una stringa arbitraria come argomento da utilizzare nello script

Esempio:

[[email protected]]$ ./script.py FOOBAR -a -b 
Running "script.py"... 
You set the option "-a" 
You set the option "-b" 
You passed the string "FOOBAR" 

Idealmente, mi piacerebbe la posizione degli argomenti per non importa. cioè:

./script.py -a FOOBAR -b == == ./script.py -a -b FOOBAR./script.py FOOBAR -a -b


in bash, posso fare questo durante l'utilizzo di getopts. Dopo aver toccato tutti gli interruttori desiderati in un ciclo caso, mi piacerebbe avere una linea che legge shift $((OPTIND-1)), e da lì posso accedere a tutti gli argomenti restanti utilizzando lo standard $1, $2, $3, ecc ...
Fa qualcosa di simile exisit per argparse?

+3

Hai seguito il tutorial di argparse? Tutto ciò che stai descrivendo è lì – SheetJS

+0

L'unica parte non discussa di iirc è il comportamento 'nargs =" * "' (in modo che un argomento posizionale possa afferrare tutti gli argomenti rimanenti) – SheetJS

+1

@Nirk, La cosa complicata è che se usi semplicemente 'parse_args', non appena vede un argomento" posizionale ", smette di cercare gli altri argomenti e raggruppa gli argomenti dall'argomento posizionale alla fine. Questo nella maggior parte dei casi va bene, ma romperebbe il suo primo e terzo esempio. – jedwards

risposta

6

per ottenere esattamente quello che stai cercando, il trucco è quello di utilizzare parse_known_args() invece di parse_args():

#!/bin/env python 

import argparse 

parser = argparse.ArgumentParser() 
parser.add_argument('-a', action="store_true") 
parser.add_argument('-b', action="store_true") 

opts = parser.parse_known_args() 
# Print info about flags 
if opts[0].a: print('You set the option "-a"') 
if opts[0].b: print('You set the option "-b"') 
# Collect remainder (opts[1] is a list (possibly empty) of all remaining args) 
if opts[1]: print('You passed the strings %s' % opts[1]) 

EDIT:

Il codice precedente visualizza le seguenti informazioni di aiuto:

 
./clargs.py -h 

usage: clargs_old.py [-h] [-a] [-b] 

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

Se si desidera informare l'utente sull'argomento arbitrario facoltativo, l'unica soluzione che posso pensare è sottoclasse ArgumentParser e scrivilo in te stesso

Ad esempio:

#!/bin/env python 

import os 
import argparse 

class MyParser(argparse.ArgumentParser): 
    def format_help(self): 
     help = super(MyParser, self).format_help() 
     helplines = help.splitlines() 
     helplines[0] += ' [FOO]' 
     helplines.append(' FOO   some description of FOO') 
     helplines.append('') # Just a trick to force a linesep at the end 
     return os.linesep.join(helplines) 

parser = MyParser() 
parser.add_argument('-a', action="store_true") 
parser.add_argument('-b', action="store_true") 

opts = parser.parse_known_args() 
# Print info about flags 
if opts[0].a: print('You set the option "-a"') 
if opts[0].b: print('You set the option "-b"') 
# Collect remainder 
if opts[1]: print('You passed the strings %s' % opts[1]) 

che visualizza le seguenti informazioni di aiuto:

 
./clargs.py -h 

usage: clargs.py [-h] [-a] [-b] [FOO] 

optional arguments: 
    -h, --help show this help message and exit 
    -a 
    -b 
    FOO   some description of FOO 

nota l'aggiunta del [FOO] nella linea di "utilizzo" e il FOO nella Guida sotto "argomenti opzionali ".

+0

Questo è buono, tranne che perdo la finestra di dialogo di aiuto integrata da argparse per la stringa opzionale. – svenglar

+1

Questo è vero. L'unica soluzione che posso pensare è sottoclassi ArgumentParser e scriverlo in te stesso. Nota che l'unica ragione per cui devi saltare attraverso questo telaio è perché vuoi che qualsiasi ordine degli argomenti funzioni.Modificherò la mia risposta con un esempio di sottoclasse di ArgumentParser. – jedwards

+0

Wow, grazie! Sembra strano che non ci sia un'opzione in argparse per avere un argomento opzionale essere una stringa arbitraria ... oh, va bene. Grazie mille per questa risposta. – svenglar

Problemi correlati