python:互斥的位置参数

时间:2016-08-27 11:46:24

标签: python argparse

我希望我的程序接受互斥的位置参数,用法显示为一组参数。
目前我只能实现其中一个,但不能同时实现两个......

这就是我目前所拥有的:

def parse_arguments():
    arg_parser = argparse.ArgumentParser(description = 'Project Builder')

    query_parser = arg_parser.add_argument_group('query', "Query current state")
    build_parser = arg_parser.add_argument_group('build', "Build project")

    # query arguments
    query_parser.add_argument('-s', '--servers',
                 action   = 'store_true',
                 required = False,
                 help     = 'Display available servers')

    query_parser.add_argument('-u', '--users',
                 action   = 'store_true',
                 required = False,
                 help     = 'Display current users')



    # build arguments
    build_parser.add_argument('-f', '--force',
                 action   = 'store',
                 required = False,
                 metavar  = 'SERVER_NAME',
                 help     = 'Force build on SERVER_NAME')

    build_parser.add_argument('-c', '--clean',
                 action   = 'store_true',
                 required = False,
                 help     = 'Clean repo before build')

    build_parser.add_argument('-v', '--verbosity',
                 action   = 'store_true',
                 required = False,
                 help     = 'Print stderr to console')

    build_parser.add_argument('-p', '--project',
                 action   = 'store',
                 required = True,
                 metavar  = 'project_A|project_B|project_C',
                 type     = project_name,
                 help     = 'Project to build (required)')

    return vars(arg_parser.parse_args())


args = parse_arguments()

其中包含以下内容:

usage: test.py [-h] [-s] [-u] [-f SERVER_NAME] [-c] [-v] -p
               project_A|project_B|project_C

Project Builder

optional arguments:
  -h, --help            show this help message and exit

query:
  Query current state

  -s, --servers         Display available servers
  -u, --users           Display current users

build:
  Build project

  -f SERVER_NAME, --force SERVER_NAME
                        Force build on SERVER_NAME
  -c, --clean           Clean repo before build
  -v, --verbosity       Print stderr to console
  -p project_A|project_B|project_C, --project project_A|project_B|project_C
                        Project to build (required)

但我真正想要的是querybuild是两个相互排斥的位置参数。

我尝试使用subparsers如下:

def parse_arguments():
    arg_parser = argparse.ArgumentParser(description = 'Project Builder')
    command_parser = arg_parser.add_subparsers(help = "Command")

    query_parser = command_parser.add_parser('query', help = "Query current state")
    build_parser = command_parser.add_parser('build', help = "Build project")

    # query arguments
    query_parser.add_argument('-s', '--servers',
                 action   = 'store_true',
                 required = False,
                 help     = 'Display available servers')

    query_parser.add_argument('-u', '--users',
                 action   = 'store_true',
                 required = False,
                 help     = 'Display current users')



    # build arguments
    build_parser.add_argument('-f', '--force',
                 action   = 'store',
                 required = False,
                 metavar  = 'SERVER_NAME',
                 help     = 'Force build on SERVER_NAME')

    build_parser.add_argument('-c', '--clean',
                 action   = 'store_true',
                 required = False,
                 help     = 'Clean repo before build')

    build_parser.add_argument('-v', '--verbosity',
                 action   = 'store_true',
                 required = False,
                 help     = 'Print stderr to console')

    build_parser.add_argument('-p', '--project',
                 action   = 'store',
                 required = True,
                 metavar  = 'project_A|project_B|project_C',
                 type     = project_name,
                 help     = 'Project to build (required)')

    return vars(arg_parser.parse_args())

但这会产生以下结果:

usage: test.py [-h] {query,build} ...

Project Builder

positional arguments:
  {query,build}  Command
    query        Query current state
    build        Build project

optional arguments:
  -h, --help     show this help message and exit

我想要的是上述两次尝试的组合,即:

usage: test.py [-h] {query,build} ...

Project Builder

optional arguments:
  -h, --help            show this help message and exit

query:
  Query current state

  -s, --servers         Display available servers
  -u, --users           Display current users

build:
  Build project

  -f SERVER_NAME, --force SERVER_NAME
                        Force build on SERVER_NAME
  -c, --clean           Clean repo before build
  -v, --verbosity       Print stderr to console
  -p project_A|project_B|project_C, --project project_A|project_B|project_C
                        Project to build (required)

querybuild互相排斥 我知道ArgumentParser.add_mutually_exclusive_group(required=False)方法,但使用它并没有帮助实现我想要的东西,因为1)参数在使用时必须是可选的,2)usage格式不像我想要。

1 个答案:

答案 0 :(得分:0)

在第一种情况下,您可以提供long int n, n2, j = 0, count = 0; cin >> n; n2 = n * n; vector<long> arr (n); for (int i = 1; i < n; i++) { if (n2 % i == 0) { arr[j] = i; j++; } } for (int i = 0; i < j; i++) { if (n % arr[i] != 0) count++; } cout << count; 个选项

-p

或作为位置

build_parser.add_argument('-p', '--project',
             action   = 'store',    # default
             required = True,
             choices  = ['project_A','project_B','project_C'],
             # type     = project_name,    # doesn't make sense
             help     = 'Project to build (required)')

build_parser.add_argument('project', choices = ['project_A','project_B','project_C'], help = 'Project to build') 必须是一个函数,可以将字符串转换为您想要的函数,例如typeint('1')

subparsers的使用类似。对于主解析器,subparser参数只是一个带有选择的位置。但是所采取的行动是将其余参数的解析解析为subparser。

两个相互排斥的定位没有逻辑意义

float('12.343')

根据位置,它无法判断您是要将字符串分配给 `[foo | bar]` 还是foo。但您有兴趣根据值分配值,或者将值限制为一组选择。

不仔细查看它的子分析程序代码看起来是正确的,并且应该根据需要解析输入。你测试过了吗?

subparsers的帮助显示并不像它可能的那样灵活,但是重新加工它需要相当多的工作(有关于此的SO问题)。当前设置是为主解析器和每个子分析器提供单独的帮助显示。没有内置的全面帮助显示。