在Python中使用命令行参数来运行两个脚本之一

10 浏览
0 Comments

在Python中使用命令行参数来运行两个脚本之一

我的包的结构如下:\n

mypackage
|-__main__.py
|-__init__.py
|-model
  |-__init__.py
  |-modelfile.py
|-simulation
  |-sim1.py
  |-sim2.py

\n文件__main__.py的内容如下:\n

from mypackage.simulation import sim1
if __name__ == '__main__':
    sim1

\n所以当我执行python -m mypackage时,脚本sim1.py会运行。\n现在我想在命令行中添加一个参数,这样python -m mypackage sim1会运行sim1.pypython -m mypackage sim2会运行sim2.py。\n我尝试了以下代码:\n

import sys
from mypackage.simulation import sim1,sim2
if __name__ == '__main__':
    for arg in sys.argv:
        arg

\n但它运行了两个脚本,而不是传递的一个脚本。\n在sim1.pysim2.py中,我有以下代码:\n

from mypackage.model import modelfile
print('modelfile.ModelClass.someattr')

0
0 Comments

问题的原因是代码中的sim1没有调用函数,正确的语法应该是sim1()。解决方法是在命令行中使用字符串映射到内部函数,并在命令行参数中使用该字符串来调用相应的函数。可以使用if语句来实现这个映射,也可以使用字典来简化代码。使用字典的方法可以确保只允许用户访问命令行中指定的Python符号,避免了安全问题。如果sim1是一个模块名,而不是一个函数名,可以使用__import__()函数在用户明确请求时导入模块。另外,建议使用第三方库click来实现将选定的函数作为Python脚本的“子命令”暴露出来的功能。总之,解决方法主要是使用if语句或字典来实现命令行参数与函数的映射关系,并注意安全问题。

0
0 Comments

在这个问题中,出现了一个函数被重复调用的情况。当将`sim1`模块导入到`main.py`中,并调用它的函数`simulation1`时,会导致`This is simulation 1`被打印两次。这是因为`simulation1`在`sim1.py`中被调用了一次,在`main.py`中又被调用了一次。

为了解决这个问题,可以将函数`simulation1`放在`if __name__ == "__main__":`语句块中。这样,当`sim1.py`作为主程序被运行时,函数会被执行,而当它被导入到其他模块时,函数不会被执行。

下面是修改后的代码:

sim1.py

def simulation1():
    print("This is simulation 1")
if __name__ == "__main__":
    simulation1()

main.py

import sim1
sim1.simulation1()

output

This is simulation 1

通过将函数放在`if __name__ == "__main__":`语句块中,现在只会打印一次`This is simulation 1`。这是因为在`main.py`中导入`sim1`模块时,`if __name__ == "__main__":`语句块不会被执行。只有当`sim1.py`作为主程序被运行时,`if __name__ == "__main__":`语句块才会执行。这样,我们可以控制在不同情况下是否执行函数。

0
0 Comments

在Python中,通过命令行参数运行两个脚本中的一个脚本,可以使用__import__函数来导入模块。具体操作如下:

首先,我们有一个主程序example.py,代码如下:

import sys
if __name__ == '__main__':
    for arg in sys.argv[1:]:
        module=__import__(arg)
        print(arg, module.foo(1))

注意,sys.argv[0]包含程序的名称。

然后,有一个sim1.py脚本,代码如下:

print('sim1')
def foo(n):
    return n+1

还有一个sim2.py脚本,代码如下:

print('sim2')
def foo(n):
    return n+2

接着,我们可以通过以下命令来运行程序并输出结果:

python example.py sim1 sim2

输出如下:

sim1
sim1 2
sim2
sim2 3

如果我们使用if __name__ == '__main__': for arg in sys.argv: __import__(arg)来导入模块,并执行python -m mypackage sim1命令,将会返回ModuleNotFoundError错误。

为了解决这个问题,我们需要注意参数的顺序,因为第一个参数是程序的名称,所以我们应该跳过它。具体细节可以参考上面的例子。

然而,即使按照上面的方法进行操作,仍然会出现ModuleNotFoundError错误。

为了解决这个问题,我们需要将__import__的结果赋值给全局命名空间,以便将符号名作为模块暴露出来。具体可参考上面的例子。在这个答案中,代码将其赋值给了new_module,或者在后面的例子中直接丢弃了它。但是,如果所有有用的操作都发生在import时,能够通过原始名称引用模块似乎并不那么重要。

0