2012-01-27 2 views
26

Я только начинаю с python, поэтому я борюсь с довольно простым примером. В основном я хочу передать имя исполняемого файла, а также входные данные с помощью аргументов командной строки и т.д .:Параметры командной строки Python

python myprogram refprogram.exe refinput.txt 

Это означает, что при выполнении myprogram, он выполняет refprogram.exe и передает ей в качестве аргумента refinput. Я попытался сделать это следующим образом:

import sys, string, os 
print sys.argv 

res = os.system(sys.argv(1)) sys.argv(2) 
print res 

Сообщение об ошибке я получаю это:

res = os.system(sys.argv(1)) sys.argv(2) 
         ^
SyntaxError: invalid syntax 

Любой идея, что я делаю не так?

Я бегу на Python 2.7

+3

Я хочу, чтобы мой компьютер дал бы мне массаж ошибки. :-) – LarsH

ответ

61

Эта линия

res = os.system(sys.argv(1)) sys.argv(2) 

неправильно в нескольких направлениях.

Во-первых, sys.ARGV список, поэтому можно использовать квадратные скобки для доступа к содержимому:

sys.argv[1] 
sys.argv[2] 

Во-вторых, вы закрываете свои скобки на os.system слишком рано, и sys.argv(2) остается висит на конце. Вы хотите переместить закрывающую скобку до самого конца строки, после всех аргументов.

В-третьих, вам нужно отделить аргументы запятыми, простое пространство не будет выполнено.

Ваша последняя строка должна выглядеть следующим образом:

res = os.system(sys.argv[1], sys.argv[2]) 
8

sys.argv список, и индексируется с помощью квадратных скобок, например, sys.argv[1]. Вы можете проверить len(sys.argv) перед его индексированием.

Кроме того, если вы хотите передать параметры os.system(), вам может понадобиться что-то вроде os.system(' '.join(sys.argv[1:])), но это не будет работать для аргументов с пробелами. Вам лучше использовать модуль подпроцесса.

3

sys.argv список

import sys, string, os 
print sys.argv 

res = os.system(sys.argv[1]) sys.argv[2] 
print res 
1

Если вы работаете в Python 2.7 рекомендуется использовать новый subprocess модуль.

В этом случае можно было бы написать

import sys, subprocess 
result = subprocess.check_output(sys.argv[1], sys.argv[2]) 
29

Далеко, далеко лучший способ сделать это с argparse library. Библиотека envoy wrapper упрощает работу с subprocess.

Простой пример:

import argparse 
import envoy 

def main(**kwargs): 
    for key, value in kwargs.iteritems(): 
     print key, value 
    cmd = '{0} {1}'.format(kwargs['program'], ' '.join(kwargs['infiles'])) 
    r = envoy.run(cmd) 
    print r.std_out 
    print r.std_err 

if __name__ == '__main__': 
    parser = argparse.ArgumentParser(description='Get a program and run it with input', version='%(prog)s 1.0') 
    parser.add_argument('program', type=str, help='Program name') 
    parser.add_argument('infiles', nargs='+', type=str, help='Input text files') 
    parser.add_argument('--out', type=str, default='temp.txt', help='name of output file') 
    args = parser.parse_args() 
    main(**vars(args)) 

Об этом говорится в аргументах, разбирает их, а затем отправляет их в основной метод в качестве словаря ключевых слов и значений. Это позволяет вам протестировать свой основной метод независимо от вашего кода аргумента, передав в предварительно сконструированный словарь.

Основной метод печатает ключевые слова и значения. Затем он создает командную строку и передает ее посланнику для запуска. Наконец, он печатает выходные данные из команды.

Если у вас установлен прут, посланник может быть установлен с pip install envoy. Самый простой способ получить pip - это pip-installer.

+2

Согласовано вообще (argparse - это потрясающе), хотя для скрипта utrity для новичков это может быть излишним. – delnan

+3

@delnan Решает так много проблем, что я думаю, что лучше просто укусить пулю и изучить ее. Я также добавил немного об использовании 'envoy' вместо' os.command', так как я пропустил это в исходном вопросе. –

+4

Это никогда не бывает излишним. Утилитные скрипты имеют способ стать постоянными производственными функциями. –

Смежные вопросы