Na początku myślałem, że tak samo jak jcollado, ale potem jest fakt, że jeśli kolejny (top level) pozycyjne argumenty mają określoną nargs
(nargs
= None
, nargs
= liczba całkowita), to działa zgodnie z oczekiwaniami. Nie powiedzie się, gdy nargs
jest lub '*'
, a czasami, gdy jest to '+'
. Więc poszedłem do kodu, aby dowiedzieć się, co się dzieje.
Sprowadza się to do sposobu podziału argumentów na zużyte. Aby dowiedzieć się, kto ma co, wywołanie parse_args
podsumowuje argumenty w łańcuchu, takim jak 'AA'
, w twoim przypadku ('A'
dla argumentów pozycyjnych, 'O'
dla opcjonalnych), a kończy się tworzeniem wzorca regex do dopasowania do tego ciągu podsumowującego, w zależności od o działaniach dodanych do analizatora składni za pomocą metod.
W każdym przypadku, na przykład, ciąg argumentów kończy się na 'AA'
. Jakie zmiany to dopasowywany wzorzec (można zobaczyć możliwe wzorce pod _get_nargs_pattern
w argparse.py
. Dla subpositional
kończy się to '(-*A[-AO]*)'
, co oznacza, że zezwala na jeden argument, po którym następuje dowolna liczba opcji lub argumentów:.Dla positional
, zależy od wartości przekazanej nargs
:
None
=>'(-*A-*)'
- 3 =>
'(-*A-*A-*A-*)'
(jeden '-*A'
za oczekiwanego argument)
'?'
=>'(-*A?-*)'
'*'
=>'(-*[A-]*)'
'+'
=>'(-*A[A-]*)'
Te wzory są dołączane, a dla nargs=None
(Twój przykład pracy), możesz skończyć z '(-*A[-AO]*)(-*A-*)'
, który pasuje dwie grupy ['A', 'A']
. W ten sposób subpositional
będzie analizować tylko subpositional
(co chcesz), podczas gdy positional
dopasuje swoją akcję.
W przypadku nargs='?'
użytkownik otrzymuje jednak '(-*A[-AO]*)(-*A?-*)'
. Druga grupa składa się w całości z opcjonalnych wzorów, a *
jest chciwy, co oznacza, że pierwsza grupa globs wszystko w ciągu znaków, kończąc rozpoznawanie dwóch grup ['AA', '']
. Oznacza to, że subpositional
dostaje dwa argumenty i oczywiście kończy się zadławieniem.
Wystarczająco zabawne, wzorzec dla nargs='+'
to '(-*A[-AO]*)(-*A[A-]*)'
, który działa , o ile tylko przekazuje jeden argument. Powiedz subpositional a
, ponieważ potrzebujesz co najmniej jednego argumentu pozycyjnego w drugiej grupie. Ponownie, ponieważ pierwsza grupa jest chciwa, przekazując subpositional a b c d
dostajesz ['AAAA', 'A']
, co nie jest tym, czego potrzebujesz.
W skrócie: bałagan. Myślę, że to powinno być uznane za błąd, ale nie wiem, jaki wpływ będzie, jeśli wzory są włączone do nich non-chciwych ...
Btw, wydaje się [znany bug ] (http://bugs.python.org/issue9340), który został naprawiony dla ostatnich wersji Pythona. –