为什么在导入模块时Python运行我的模块,以及如何停止它?

问题:为什么在导入模块时Python运行我的模块,以及如何停止它?

我有一个正在构建的Python程序,可以通过以下两种方式之一运行:第一种是调用“ python main.py”,它以友好的方式提示用户输入,然后通过该程序运行用户输入。另一种方法是调用“ python batch.py -file- ”,它将遍历所有友好的输入集合,并通过该程序一次运行整个文件的输入值。

问题是,当我运行“ batch.py​​”时,它会从“ main.py”中导入一些变量/方法/等,并在运行此代码时:

import main

在程序的第一行,它立即错误,因为它试图运行“ main.py”中的代码。

如何阻止Python运行要导入的“主”模块中包含的代码?

I have a Python program I’m building that can be run in either of 2 ways: the first is to call “python main.py” which prompts the user for input in a friendly manner and then runs the user input through the program. The other way is to call “python batch.py -file-” which will pass over all the friendly input gathering and run an entire file’s worth of input through the program in a single go.

The problem is that when I run “batch.py” it imports some variables/methods/etc from “main.py”, and when it runs this code:

import main

at the first line of the program, it immediately errors because it tries to run the code in “main.py”.

How can I stop Python from running the code contained in the “main” module which I’m importing?


回答 0

因为这就是Python的工作方式,诸如classand之def类的关键字不是声明。相反,它们是执行的真实实时语句。如果未执行,则您的模块将为..空:-)

无论如何,惯用的方法是:

# stuff to run always here such as class/def
def main():
    pass

if __name__ == "__main__":
   # stuff only to run when not called via 'import' here
   main()

请参阅目的是什么if __name__ == "__main__"

但是,它确实需要对要import编辑的模块进行源代码控制。

快乐的编码。

Because this is just how Python works – keywords such as class and def are not declarations. Instead, they are real live statements which are executed. If they were not executed your module would be .. empty :-)

Anyway, the idiomatic approach is:

# stuff to run always here such as class/def
def main():
    pass

if __name__ == "__main__":
   # stuff only to run when not called via 'import' here
   main()

See What is if __name__ == "__main__" for?

It does require source control over the module being imported, however.

Happy coding.


回答 1

由于Python的工作方式,在导入模块时必须运行模块。

为了防止模块中的代码在导入时被执行,而只能在直接运行时执行,可以使用以下方法进行保护if

if __name__ == "__main__":
    # this won't be run when imported

您可能需要将此代码放入main()方法中,以便可以直接执行文件,或导入模块并调用main()。例如,假设它在file中foo.py

def main():
    print "Hello World"

if __name__ == "__main__":
    main()

该程序可以通过运行python foo.py或从另一个Python脚本运行:

import foo

...

foo.main()

Due to the way Python works, it is necessary for it to run your modules when it imports them.

To prevent code in the module from being executed when imported, but only when run directly, you can guard it with this if:

if __name__ == "__main__":
    # this won't be run when imported

You may want to put this code in a main() method, so that you can either execute the file directly, or import the module and call the main(). For example, assume this is in the file foo.py.

def main():
    print "Hello World"

if __name__ == "__main__":
    main()

This program can be run either by going python foo.py, or from another Python script:

import foo

...

foo.main()

回答 2

使用if __name__ == '__main__'惯用语- __name__是一个特殊变量,其值是'__main__'模块是否作为脚本运行时的值,模块名称(如果已导入)。所以你会做类似的事情

# imports
# class/function definitions
if __name__ == '__main__':
    # code here will only run when you invoke 'python main.py'

Use the if __name__ == '__main__' idiom — __name__ is a special variable whose value is '__main__' if the module is being run as a script, and the module name if it’s imported. So you’d do something like

# imports
# class/function definitions
if __name__ == '__main__':
    # code here will only run when you invoke 'python main.py'

回答 3

不幸的是,您没有。这是导入语法工作方式的一部分,并且重要的是,请记住这一点-记住def实际上是已执行某项操作,如果Python不执行导入,那么您将被困在没有函数的情况下。

但是,由于您可能可以访问该文件,因此您可以查看并查看导致该错误的原因。可能有可能修改您的环境以防止发生错误。

Unfortunately, you don’t. That is part of how the import syntax works and it is important that it does so — remember def is actually something executed, if Python did not execute the import, you’d be, well, stuck without functions.

Since you probably have access to the file, though, you might be able to look and see what causes the error. It might be possible to modify your environment to prevent the error from happening.


回答 4

将代码放入函数中,直到调用该函数,该代码才会运行。您应该在其中具有主要功能main.py。带有以下语句:

if __name__ == '__main__':
  main()

然后,如果调用python main.pymain()函数将运行。如果导入main.py,则不会。另外,main.py为清楚起见,您可能应该重命名为其他名称。

Put the code inside a function and it won’t run until you call the function. You should have a main function in your main.py. with the statement:

if __name__ == '__main__':
  main()

Then, if you call python main.py the main() function will run. If you import main.py, it will not. Also, you should probably rename main.py to something else for clarity’s sake.


回答 5

有一个Python增强建议PEP 299,旨在用替换if __name__ == '__main__':成语def __main__:,但遭到拒绝。了解使用时要记住的内容仍然是一本好书if __name__ = '__main__':

There was a Python enhancement proposal PEP 299 which aimed to replace if __name__ == '__main__': idiom with def __main__:, but it was rejected. It’s still a good read to know what to keep in mind when using if __name__ = '__main__':.


回答 6

您可以这样编写“ main.py”:

#!/usr/bin/env python

__all__=["somevar", "do_something"]

somevar=""

def do_something():
    pass #blahblah

if __name__=="__main__":
    do_something()

You may write your “main.py” like this:

#!/usr/bin/env python

__all__=["somevar", "do_something"]

somevar=""

def do_something():
    pass #blahblah

if __name__=="__main__":
    do_something()

回答 7

尽管import不运行代码就无法使用;您可以通过很快速的方式输入变量;通过使用numpy.savez,将变量作为numpy数组存储在.npz文件中。之后,您可以使用加载变量numpy.load

查看scipy文档中的完整描述

请注意,这仅适用于变量和变量数组,而不适用于方法等。

Although you cannot use import without running the code; there is quite a swift way in which you can input your variables; by using numpy.savez, which stores variables as numpy arrays in a .npz file. Afterwards you can load the variables using numpy.load.

See a full description in the scipy documentation

Please note this is only the case for variables and arrays of variable, and not for methods, etc.


回答 8

尝试仅从main.py导入所需的功能?所以,

from main import SomeFunction

可能是因为您在batch.py​​中命名的函数与main.py中的命名相同,并且在导入main.py时,程序将运行main.py函数而不是batch.py​​函数;执行以上操作可以解决该问题。我希望。

Try just importing the functions needed from main.py? So,

from main import SomeFunction

It could be that you’ve named a function in batch.py the same as one in main.py, and when you import main.py the program runs the main.py function instead of the batch.py function; doing the above should fix that. I hope.