通过命令行传递Python变量?

5

我是 Python 的新手(意思是说,昨天才开始学),如果我还不知道“显而易见”的东西,请多包涵。

我有两种方法可以解决这个问题,其中任何一种对我来说都可以,但我不确定 getoptoptparse 是否包含我想要/需要的内容(根据我所读的)? 我想做类似以下的事情:

python this.py --variable VariableName="Value" -v VariableName2="Value2"

或者

python this.py --VariableName "Value"

我面临的主要问题是,我可能需要选择性地传递其中任何变量,但不一定是全部变量,也不一定是任何特定顺序(因此,原始的sys.argv在这种情况下行不通)。对于其中一些变量,我可能会传递字符串、数字和/或数组。

一旦变量被传递到脚本中,我需要检查它们是否设置/非空,并根据需要分配默认值。

谢谢!

3个回答

7
您肯定需要一个命令行参数解析器。Python附带了一些。Python2.7有argparse,它可以根据需要回溯到早期版本,并且是我推荐的。还有optparse。它不如argparse好用,但是旧版的Python和新版的Python都可以使用。

还有getopt,但与其他解析器相比,这个几乎不值得一提。


2

我将自己的问题作为第一个回答。

尽管我很喜欢@mgilson提供的答案,但我找到了一种“更简单”的方法。我非常熟悉正则表达式,并且弄清楚关联数组(即字典)并不太困难。

import re

args = {}
args['pythonFile'] =  sys.argv[0]

for arg in sys.argv[1:]:
  variable = re.search('\-\-(.*)\=',arg)
  variable = variable.group(1)
  value = re.search('\=(.*)',arg)
  value = value.group(1)
  args[variable] = value

print args

这是证明:

$ /opt/python27/bin/python2.7 Test.py --var1=1 --var2="Testing This"
{'var1': '1', 'pythonFile': 'Test.py', 'var2': 'Testing This'}

哇!


2
虽然这听起来非常聪明(确实如此),但据我所见,也许并不是实现您真正想要的最“pythonic”的方法。但别担心,随着您使用它们的次数越来越多,您很快就会自然而然地吸收Python的特性并使用它们。 - heltonbiker
哈,谢谢,当我写下这段代码时,我相当确定那就是情况。不过随着我的学习深入,我会变得更好,但现在对于任何和我一样初学者来说,可能会有所帮助。 - Jon Lawton
3
学而后行与立即采取有效方法之间的平衡取决于解决问题与学习工具之间的需求平衡。但我想这适用于每个问题与工具关系...(深度优先搜索可能会让人瘫痪不前...) - heltonbiker

1
我稍微重构了上面的代码,使其更加灵活和模块化(顺便说一句,这是一个很棒的解决方案)。现在你可以添加类似于--dev而不是--dev=true的内容。或者两者都可以。如果你没有添加任何参数,它也不会导致应用程序崩溃。
def get_cli_args():
    """
    Returns a dictionary of arguments passed to through the CLI.
    """

    import re
    import sys

    args = {}

    for arg in sys.argv[1:]:
        var = re.search('\-\-([A-Za-z]*)', arg) # optional value assignment
        var = var.group(1)
        value = re.search('\=(.*)', arg)
        value = value.group(1) if value else None
        args[var] = value

    return args

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接