2017-10-12 87 views
1


我需要解析的命令行字符串是這樣的:如何解析與選項混合的幾個位置參數?

node frontend.js project1.pro project2.pro ... projectN.pro --spec linux-g++ CONFIG+=debug CONFIG+=qml_debug -opt1 value1 ... -opt2 value2 

即選項(連字符)和位置參數(沒有它在啓動) 可以通過用戶:(

混合我試圖指定的幾個位置參數,但是這是不行的:

parser = argparse.ArgumentParser(prog='PROG') 
parser.add_argument('--foo') 
parser.add_argument('project_files', default=[], nargs='+') 
parser.add_argument('-spec', nargs=1, required=True) 
parser.add_argument('other_options', default=[], nargs='+') 
print(parser.parse_args('--foo B project_1.pro project_2.pro -spec linux-g++ CONFIG+=debug CONFIG+=qml_debug'.split())) 

,但得到這樣的錯誤:

PROG: error: unrecognized arguments: CONFIG+=debug CONFIG+=qml_debug 

什麼做錯了 感謝

PS很抱歉,如果這個問題是愚蠢的,我是新的?!在Python中使用這些庫進行參數解析。
P.P.S.參數 「節點frontend.js」 被忽略

回答

1
print(parser.parse_args('--foo B project_1.pro project_2.pro -spec linux-g++'.split())) 

產生

Namespace(foo='B', other_options=['project_2.pro'], project_files=['project_1.pro'], spec=['linux-g++']) 

'progject_2.pro' 被分配給other_options而不是project_files。這是因爲如何處理2 nargs='+'

parse_args候補處理定位和可選項(標記)。它試圖處理儘可能多的定位。這可能會導致意想不到的結果,當其中一個或多個具有這些'開放式'nargs+*

我建議改爲:

parser = argparse.ArgumentParser(prog='PROG') 
parser.add_argument('--foo') 
parser.add_argument('project_files', nargs='+') 
parser.add_argument('--spec') 
parser.add_argument('--other', nargs='+') 
print(parser.parse_args('--foo B project_1.pro project_2.pro --spec linux-g++'.split())) 

print(parser.parse_args('--foo B project_1.pro project_2.pro --spec linux-g++ --other CONFIG+=debug CONFIG+=qml_debug'.split())) 

導致

2343:~/mypy$ python stack46702635.py 
Namespace(foo='B', other=None, project_files=['project_1.pro', 'project_2.pro'], spec='linux-g++') 
Namespace(foo='B', other=['CONFIG+=debug', 'CONFIG+=qml_debug'], project_files=['project_1.pro', 'project_2.pro'], spec='linux-g++') 

https://bugs.python.org/issue15112 - argparse: nargs='*' positional argument doesn't accept any items if preceded by an option and another positional

https://bugs.python.org/issue9338 - argparse optionals with nargs='?', '*' or '+' can't be followed by positionals


您可以省略other參數,並使用parse_known_args。未知字符串將在單獨的列表中返回。

#parser.add_argument('other', nargs='...') 
print(parser.parse_known_args('--foo B project_1.pro project_2.pro --spec linux-g++'.split())) 

print(parser.parse_known_args('--foo B project_1.pro project_2.pro --spec linux-g++ CONFIG+=debug CONFIG+=qml_debug'.split())) 

0859:~/mypy$ python stack46702635.py 
(Namespace(foo='B', project_files=['project_1.pro', 'project_2.pro'], spec='linux-g++'), []) 
(Namespace(foo='B', project_files=['project_1.pro', 'project_2.pro'], spec='linux-g++'), ['CONFIG+=debug', 'CONFIG+=qml_debug']) 

optparsegetopt早些時候解析器只是處理的標記參數,並返回剩下的列表。你必須自己解析這些。

+0

因此,可以有兩組或更多組位置參數,用「常規」選項分隔 - 或者argparse不能這樣做? – eraxillan

+0

UPD:一個問題是我應該支持其他應用程序(Qt qmake)的命令行格式,所以我不能更改選項格式:( – eraxillan

+0

「-spec」定義在兩個位置之間並不重要。解析是由命令行中的順序決定的。有幾個關於改進這種處理的錯誤/問題,但沒有做出正式的修改。 – hpaulj

相關問題