我在Python 2.7中使用argparse来解析输入选项。我的选项之一是多项选择。我想在它的帮助文本中做一个列表。
from argparse import ArgumentParser
parser = ArgumentParser(description='test')
parser.add_argument('-g', choices=['a', 'b', 'g', 'd', 'e'], default='a',
help="Some option, where\n"
" a = alpha\n"
" b = beta\n"
" g = gamma\n"
" d = delta\n"
" e = epsilon")
parser.parse_args()
然而,argparse会删除所有换行和连续的空格。结果如下所示
~/Downloads:52$ python2.7 x.py -h
usage: x.py [-h] [-g {a,b,g,d,e}]
test
optional arguments:
-h, --help show this help message and exit
-g {a,b,g,d,e} Some option, where a = alpha b = beta g = gamma d = delta e
= epsilon
如何在帮助文本中插入换行?
我想在描述文本中有手动换行符,并自动换行;但是这里没有一个建议对我有用-所以我最终修改了答案中给出的SmartFormatter类;尽管argparse方法名不是一个公共API,但这是我拥有的(作为一个名为test.py的文件):
import argparse
from argparse import RawDescriptionHelpFormatter
# call with: python test.py -h
class SmartDescriptionFormatter(argparse.RawDescriptionHelpFormatter):
#def _split_lines(self, text, width): # RawTextHelpFormatter, although function name might change depending on Python
def _fill_text(self, text, width, indent): # RawDescriptionHelpFormatter, although function name might change depending on Python
#print("splot",text)
if text.startswith('R|'):
paragraphs = text[2:].splitlines()
rebroken = [argparse._textwrap.wrap(tpar, width) for tpar in paragraphs]
#print(rebroken)
rebrokenstr = []
for tlinearr in rebroken:
if (len(tlinearr) == 0):
rebrokenstr.append("")
else:
for tlinepiece in tlinearr:
rebrokenstr.append(tlinepiece)
#print(rebrokenstr)
return '\n'.join(rebrokenstr) #(argparse._textwrap.wrap(text[2:], width))
# this is the RawTextHelpFormatter._split_lines
#return argparse.HelpFormatter._split_lines(self, text, width)
return argparse.RawDescriptionHelpFormatter._fill_text(self, text, width, indent)
parser = argparse.ArgumentParser(formatter_class=SmartDescriptionFormatter, description="""R|Blahbla bla blah blahh/blahbla (bla blah-blabla) a blahblah bl a blaha-blah .blah blah
Blah blah bla blahblah, bla blahblah blah blah bl blblah bl blahb; blah bl blah bl bl a blah, bla blahb bl:
blah blahblah blah bl blah blahblah""")
options = parser.parse_args()
这是它在2.7和3.4中的工作原理:
$ python test.py -h
usage: test.py [-h]
Blahbla bla blah blahh/blahbla (bla blah-blabla) a blahblah bl a blaha-blah
.blah blah
Blah blah bla blahblah, bla blahblah blah blah bl blblah bl blahb; blah bl
blah bl bl a blah, bla blahb bl:
blah blahblah blah bl blah blahblah
optional arguments:
-h, --help show this help message and exit
我承认我发现这是一个非常令人沮丧的经历,因为我看到很多解决方案,我在网上看到很多次这样的问题。但我发现这些解决方案对我来说太复杂了,我想分享我最简单的解决方案。
下面是演示的脚本:
#!/usr/bin/python3
import textwrap
from argparse import ArgumentParser, HelpFormatter
class RawFormatter(HelpFormatter):
def _fill_text(self, text, width, indent):
return "\n".join([textwrap.fill(line, width) for line in textwrap.indent(textwrap.dedent(text), indent).splitlines()])
program_descripton = f'''
FunkyTool v1.0
Created by the Funky Guy on January 1 2020
Copyright 2020. All rights reserved.
Licensed under The Hippocratic License 2.1
https://firstdonoharm.dev/
Distributed on an "AS IS" basis without warranties
or conditions of any kind, either express or implied.
USAGE:
'''
parser = ArgumentParser(description=program_descripton, formatter_class=RawFormatter)
args = parser.parse_args()
下面是它在test.py中的样子:
$ ./test.py --help
usage: test.py [-h]
FunkyTool v1.0
Created by the Funky Guy on January 1 2020
Copyright 2020. All rights reserved.
Licensed under The Hippocratic License 2.1
https://firstdonoharm.dev/
Distributed on an "AS IS" basis without warranties
or conditions of any kind, either express or implied.
USAGE:
optional arguments:
-h, --help show this help message and exit
所以,所有原始描述中的基本格式都被整齐地保留了下来,我们不得不,唉,使用一个自定义格式化器,但它是一个联机程序。它可以写得更清楚:
class RawFormatter(HelpFormatter):
def _fill_text(self, text, width, indent):
text = textwrap.dedent(text) # Strip the indent from the original python definition that plagues most of us.
text = textwrap.indent(text, indent) # Apply any requested indent.
text = text.splitlines() # Make a list of lines
text = [textwrap.fill(line, width) for line in text] # Wrap each line
text = "\n".join(text) # Join the lines again
return text
但我自己更喜欢写在一行上。
另一种简单的方法是包含文本包。
例如,
import argparse, textwrap
parser = argparse.ArgumentParser(description='some information',
usage='use "python %(prog)s --help" for more information',
formatter_class=argparse.RawTextHelpFormatter)
parser.add_argument('--argument', default=somedefault, type=sometype,
help= textwrap.dedent('''\
First line
Second line
More lines ... '''))
通过这种方式,我们可以避免在每个输出行前面有很长的空白。
usage: use "python your_python_program.py --help" for more information
Prepare input file
optional arguments:
-h, --help show this help message and exit
--argument ARGUMENT
First line
Second line
More lines ...
我来这里寻找方法来获得ArgumentDefaultsHelpFormatter的行为,但与换行符和制表符荣誉。特洛伊的代码让我接近了,但最终的结果更简单一些:
class CustomArgumentFormatter(argparse.ArgumentDefaultsHelpFormatter):
"""
Formats help text to honor newlines and tabs (and show default values).
"""
# Match multiples of regular spaces only.
_SPACE_MATCHER = re.compile(r' +', re.ASCII)
def _split_lines(self, text, width):
new_text = []
for line in text.splitlines():
# For each newline in the help message, replace any multiples of
# whitespaces (due to indentation in source code) with one space.
line = self._SPACE_MATCHER.sub(' ', line).rstrip()
# Fit the line length to the console width
new_text.extend(textwrap.wrap(line, width))
return new_text
然后换行符和制表符将按预期出现:
parser = argparse.ArgumentParser(formatter_class=CustomArgumentFormatter)
parser.add_argument(
'--ethernet_config', type=str, required=False, default=None,
help='Path to a text file that specifies Ethernet network IP settings \
to use on the board. For example: \
\n\t ip=192.0.2.100 \
\n\t subnet_mask=255.255.255.0 \
\n\t gateway=192.0.2.1')
使用RawTextHelpFormatter获取新行并处理缩进的另一种简单方法是
import argparse
parser = argparse.ArgumentParser(
description='test', formatter_class=argparse.RawTextHelpFormatter)
parser.add_argument('-g', choices=['a', 'b', 'g', 'd', 'e'], default='a',
help=('Some option, where\n'
' a = alpha\n'
' b = beta\n'
' g = gamma\n'
' d = delta\n'
' e = epsilon'))
parser.parse_args()
输出为
$ python2 x.py -h
usage: x.py [-h] [-g {a,b,g,d,e}]
test
optional arguments:
-h, --help show this help message and exit
-g {a,b,g,d,e} Some option, where
a = alpha
b = beta
g = gamma
d = delta
e = epsilon