2012-01-27 16 views
26

Właśnie zaczynam od pythona, więc walczę z dość prostym przykładem. Zasadniczo chcę przekazać nazwę pliku wykonywalnego plusa swój wkład poprzez linię argumentów polecenia, np .:Parametry wiersza polecenia Pythona

python myprogram refprogram.exe refinput.txt 

Oznacza to, że podczas wykonywania myprogram, wykonuje refprogram.exe i przechodzi do niego jako argument refinput. Próbowałem to zrobić w następujący sposób:

import sys, string, os 
print sys.argv 

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

komunikat o błędzie, który pojawia się:

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

Każdy pomysł co robię źle?

ja działa Pyton 2,7

+3

życzę mój komputer dałby mi masaż błędzie. :-) – LarsH

Odpowiedz

61

Linia ta

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

jest źle w kilka sposobów.

Po pierwsze, sys.argv jest lista, więc trzeba używać nawiasów kwadratowych, aby uzyskać dostęp do jego zawartości:

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

drugie, zamknąć swoje nawiasów na os.system zbyt szybko, a sys.argv(2) zostaje zawieszony na koniec. Chcesz przenieść nawias zamykający na sam koniec linii, po wszystkich argumentach.

Po trzecie, musisz oddzielić argumenty przecinkami, a proste spacje nie.

Twoja ostateczna linia powinna wyglądać następująco:

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

sys.argv jest na liście, jest oznaczane za pomocą wsporników kwadratowych, np sys.argv[1]. Przed indeksowaniem warto sprawdzić także len(sys.argv).

Ponadto, jeśli chcesz przekazać parametry do os.system(), możesz potrzebować czegoś takiego jak os.system(' '.join(sys.argv[1:])), ale to nie zadziała dla argumentów ze spacjami. Lepiej skorzystaj z modułu podprocesu.

3

sys.argv jest lista

import sys, string, os 
print sys.argv 

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

Jeśli używasz Pythona 2.7 zaleca się korzystać z nowego modułu subprocess.

w tym przypadku byłoby piszesz

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

Daleko, daleko lepszy sposób to zrobić, to z argparse library. Biblioteka envoy wrapper ułatwia także pracę z .

Prosty przykład:

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)) 

ten czyta w argumentach, analizuje je, a następnie wysyła je do głównego sposobu w słowniku słów kluczowych i wartości. Pozwala to przetestować główną metodę niezależnie od kodu argumentu, przekazując wstępnie skonstruowany słownik.

Główna metoda służy do drukowania słów kluczowych i wartości. Następnie tworzy ciąg poleceń i przekazuje go do wysłania do uruchomienia. Na końcu drukuje dane wyjściowe z polecenia.

Jeśli masz zainstalowaną pipę, wysłannik może być zainstalowany z pip install envoy. Najprostszym sposobem na uzyskanie pip'a jest pip-installer.

+2

Uzgodnione w ogóle (argparse jest niesamowite), choć dla skryptu dla początkujących, może to być przesada. – delnan

+3

@delnan Rozwiązuje tak wiele problemów, że myślę, że lepiej jest po prostu ukąsić kulę i nauczyć się jej. Dodałem też trochę na temat używania 'envoy' zamiast' os.command', ponieważ brakowało mi tego w oryginalnym pytaniu. –

+4

To nigdy nie jest przesada. Skrypty narzędziowe mogą stać się stałymi cechami produkcyjnymi. –

Powiązane problemy