Разбор аргументов командной строки в скрипте Python (горе getopt) - PullRequest
4 голосов
/ 14 октября 2010

Может кто-нибудь определить, почему следующий скрипт не печатает переданные аргументы?

import sys, getopt

def usage():
    print 'Unknown arguments'

def main(argv):
    try:
        opts, args = getopt.getopt(argv,'fdmse:d',['files=','data-source=','mode=','start','end'])

    except getopt.GetoptError:
        usage()
        sys.exit(999)

    for opt, arg in opts:
        # print opt,arg 
        if opt in('-f','--files'):
            print 'files: ', arg  #

if __name__ == "__main__":
    main(sys.argv[1:])

Когда я запускаю скрипт в командной строке и передаю аргументы -f=dummy.csv, вместо этого, похоже, вызывается usage() - ПОЧЕМУ?

Кстати, я нахожу логику выполнения программы немного странной (я скопировал ее из здесь ). Обычно я бы подумал, что логика будет реализована в ветви try, а затем ПОСЛЕ того, что приходит обработчик исключений.

Является ли это (как вставлено в коде выше) «питонским» способом записи блоков try / catch?

Ответы [ 3 ]

2 голосов
/ 30 ноября 2010

Ты получил ответы?

Один из способов отладки исключений Python - это переместить (или временно скопировать для отладки) код из блока try. Вы получите полный след.

И, конечно, еще один способ - уменьшить количество тестов. Здесь я сократил проблемы до трех строк и попробовал решение, на которое намекает @ s.lott (используя 'f:' в вызове getopts), а также в конце покажу, как ведет себя вызов с различными тестовыми данными: 1005 *

$ cat x1.py
import sys, getopt
opts, args = getopt.getopt(sys.argv[1:],'fdmse:d',['files=','data-source=','mode=','start','end'])
print "opts=", opts, "args=", args

$ python x1.py -f=dummy.csv argblah
Traceback (most recent call last):
  File "x1.py", line 2, in <module>
    opts, args = getopt.getopt(sys.argv[1:],'fdmse:d',['files=','data-source=','mode=','start','end'])
  File "/usr/lib/python2.6/getopt.py", line 91, in getopt
    opts, args = do_shorts(opts, args[0][1:], shortopts, args[1:])
  File "/usr/lib/python2.6/getopt.py", line 191, in do_shorts
    if short_has_arg(opt, shortopts):
  File "/usr/lib/python2.6/getopt.py", line 207, in short_has_arg
    raise GetoptError('option -%s not recognized' % opt, opt)
getopt.GetoptError: option -= not recognized

$ sed 's/fdm/f:dm/' <x1.py >x2.py

$ diff x1.py x2.py
2c2
< opts, args = getopt.getopt(sys.argv[1:],'fdmse:d',['files=','data-source=','mode=','start','end'])
---
> opts, args = getopt.getopt(sys.argv[1:],'f:dmse:d',['files=','data-source=','mode=','start','end'])

$ python x2.py -f=dummy.csv argblah
opts= [('-f', '=dummy.csv')] args= ['argblah']

$ python x1.py -f dummy.csv argblah
opts= [('-f', '')] args= ['dummy.csv', 'argblah']
1 голос
/ 14 октября 2010

Обычно, я бы подумал, что логика будет реализована в ветви try

"Обычно"?Что обычно означает?

Что должна делать программа?Какие исключения имеют смысл?Что делает программа в ответ на исключения.

Там нет "нормально".Больше, чем обычный оператор присваивания или нормальное определение функции.

Ваша программа делает то, что имеет смысл для достижения требуемого конечного состояния.Там нет "нормально".

0 голосов
/ 16 февраля 2015

Импорт и использование argparse вместо getopt. Его гораздо проще использовать, и в него встроено почти все необходимое для запуска из командной строки.

Например,

    parser = argparse.ArgumentParser(
        description='Description of what the module does when run.')
    parser.add_argument("-o", "--output", help='Path of log file.')
    args = parser.parse_args()

Так просто. Конечно, вам нужно импортировать argparse вверху вашего файла.

...