【问题标题】:Calling scripts and variables between them iteratively in Python在 Python 中迭代地调用它们之间的脚本和变量
【发布时间】:2019-06-15 18:33:30
【问题描述】:

我正在尝试使脚本自动化:

  • 读取在另一个脚本中定义的输入(例如 Input_01.py 或 Input_02.py,仅包含变量定义,例如:J = 6 或 J = 7);和
  • 在函数中使用该变量,即:

    def foo_function():
    
        A = J
        A += 3
        print(A)
    

现在,如果我不需要自动化任何东西,事情就很简单了: 我只需输入from Input_01 import J 即可。然后我可以对 Input_02 执行相同的操作并重复该操作。 但我的想法是制作一个脚本(Multi_Run.py),它允许我自动调用多次关键脚本(称为“code_foo.py”)的过程,每个输入文件一个,每次读取不同的输入文件(例如 Input_01、Input_02、...等)

这是我当前的“Multi_Run.py”脚本(针对只有两个不同输入文件的情况进行了简化):

Inputs = []
for i in range(2):
    Inputs.append("Input_0%s" % (i+1))


for Counter in Inputs:
    import code_foo
    code_foo.foo_function()

但现在我不能在“code_foo.py”中说:from Counter import J,因为这不起作用有两个原因:

  1. 首先,Counter 不是 code_foo 中的变量(这似乎可以通过添加类似 from __main__ import * 的行来解决)
  2. 其次,导入函数无法读取 Counter 变量中的字符串,但它直接需要模块的名称(例如 Input_01),从而阻止了授权。我试图通过使用 importlib.import_module 来解决这个问题,但它似乎无法正常工作(即“Input_##”模块以某种方式“导入”,而不是“运行”,这意味着“J=#somenumber”行导入脚本时未运行,因此出现错误,因为未定义 J 变量)。

为了更清楚,我当前的 code_foo.py 脚本如下:

import importlib


from __main__ import *

importlib.import_module(Counter)


def foo_function():

        A = J
        A += 3
        print(A)

有什么提示吗?非常感谢

【问题讨论】:

  • “似乎无法正常工作”是对问题的完全无用的描述。请发布您的代码(或至少一个 MCVE)和它如何“不起作用”的完整描述(如果您遇到异常,请发布确切的错误消息和完整的回溯,否则描述预期结果和结果取而代之)。
  • 感谢您的回复,我已经发布了几乎整个代码,所以让我回顾一下:我有 Multi_Run.py 脚本(正如发布的那样),两个 Input_##.py 脚本只包含“ J = #a number"(如前所述),以及 code_foo.py 脚本,目前是这样的:` import importlib from main import * importlib.import_module(Counter) def foo_function(): A = JA += 3 print(A)` 问题是使用 importlib 的导入没有像正常导入那样“运行”导入的脚本,因此变量 J 是“未知的”
  • 请编辑您的问题 - cmets 中的代码几乎不可读。
  • 感谢您的提示,我编辑了问题。如果您有任何解决方案,我将不胜感激

标签: python function variables scripting iteration


【解决方案1】:

AFAICT(您的问题仍然很不清楚),看起来您在这里有两个问题。

第一个是关于 Python 的导入和命名空间。 Python 导入不是 C 或 PHP 中的“包含”,因此导入模块不会使模块中定义的名称直接在导入器的命名空间中可用,您必须使用限定名称(“.”)。此外,Python 没有“进程全局”命名空间,Python 的“全局变量”仅对当前模块的命名空间是全局的,因此在模块“a”中定义全局名称并不会使其对模块“导入”的模块神奇地可用一种”。这意味着code_foo.py 中的foo_function 不能直接访问主脚本中定义的名称。

实际上-这是第二个问题-您的问题来自foo_function,具体取决于在其他地方定义的全局名称。这是一个设计错误。作为一般规则,你不应该在不需要全局变量时使用它们,而且你很少需要全局变量。只需编写您的函数,以便它们将“外部”值作为参数,一切都会变得更简单,更易于阅读、测试和维护。

在您的情况下,您需要做的就是 1/ 重写 foo_function() 以便将 J 作为参数和 2/ 重写 multirun 以便从您的“输入”模块中获取 J 和将其传递给foo_function:

# code_foo.py

def foo_function(j):
    a = j
    a += 3
    print(a)

# multirun.py

import importlib
import code_foo

def main():
   inputs = ["Input_0%s" % i for i in range(1,3)]

   for modname in inputs:
       module = importlib.import_module(modname)
       j = module.J 
       code_foo.foo_function(j)

if __name__ == "__main__":
    main()

附带说明:python 的命名约定是为模块和变量使用 all_lower 名称 - ALL_CAPS 名称用于伪常量。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2017-09-21
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-11-03
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多