这样做做什么,为什么应该包括:if语句?

if __name__ == "__main__":
    print("Hello, World!")

如果你试图结束一个问题 如果你想要结束一个问题 在那里有人应该应该 使用这个学说,而不是,是不是, 考虑关闭作为 重复的为什么Python在我进口时 运行我的模块? 我该如何阻止它?。而对于某些问题,如果有人只是没有调用任何函数,或者错误地期望指定函数main自动用作切入点,使用当我启动 Python 脚本时, 主函数为何不运行? 脚本从哪里开始运行 ?.


当前回答

如果 Python 口译员正在运行一个特定模块,那么__name__全局变量将拥有值"__main__":

def a():
    print("a")

def b():
    print("b")

if __name__ == "__main__":

        print ("you can see me")
        a()
else:

        print ("You can't see me")
        b()

当您运行此脚本时, 它会打印 :

you can see me
a

如果您导入此文件, 请说A要到文件的文件B,然后执行文件B时当时if __name__ == "__main__"文件中的文件A成为假假,所以它指纹:

You can't see me
b

其他回答

用于从命令行调用 Python 文件。 它通常用于调用“ main ()) ” 函数或执行其他合适的启动代码, 比如, 处理命令行参数 。

也可以以几种方式写成。

def some_function_for_instance_main():
    dosomething()


__name__ == '__main__' and some_function_for_instance_main()

我不是说你应该用这个来做生产代码, 但是它可以说明,没有什么"神奇"if __name__ == '__main__'.

这只是援引 Python 文件中主要功能的常规 。

您可以查看特殊变量__name__使用此简单示例 :

创建创建文件1. py

if __name__ == "__main__":
    print("file1 is being run directly")
else:
    print("file1 is being imported")

创建 *file2。平平

import file1 as f1

print("__name__ from file1: {}".format(f1.__name__))
print("__name__ from file2: {}".format(__name__))

if __name__ == "__main__":
    print("file2 is being run directly")
else:
    print("file2 is being imported")

执行文件2. py

Output:

file1 is being imported
__name__ from file1: file1
__name__ from file2: __main__
file2 is being run directly

让我们更抽象地看待答案:

假设我们有这个密码x.py:

...
<Block A>
if __name__ == '__main__':
    <Block B>
...

区块 A 和 B 正在运行时运行x.py.

但是,在我们运行另一个模块时,只运行A区块(而不是B区块),y.py例如,x.py导入并运行代码(例如当函数在x.py调自y.py).

有关代码的机理有很多不同之处, “如何” 但对我而言,除非我理解“为什么” , 否则这些都说不通。 这应该对新的程序员有特别的帮助。

获取文件“ ab. py ” :

def a():
    print('A function in ab file');
a()

第二个文件“xy.py”:

import ab
def main():
    print('main function: this is where the action is')
def x():
    print ('peripheral task: might be useful in other projects')
x()
if __name__ == "__main__":
    main()

这个代码到底在干嘛?

执行时执行xy.py, 您 , 您import ab。导入语句在导入时立即运行模块,因此ab业务在剩余时间之前完成xy完成后ab,它继续xy.

口译员跟踪脚本运行的脚本__name__。当您运行一个脚本时,不管你叫什么,口译员都叫它"__main__",使它成为在运行外部脚本后返回的主人或“家”脚本。

任何其它的脚本 从这里调用"__main__"将其文件名指定为脚本__name__(例如,__name__ == "ab.py"因此,线线if __name__ == "__main__":是口译员的测试, 以确定它是否在解释/ 区分最初执行的“ 家” 脚本, 或者它是否临时偷看另一个( 外部) 脚本。 这让程序员具有灵活性, 如果直接执行的话, 脚本行为会有所不同 。

让我们跨过上面的代码 来理解发生了什么, 首先关注未缩入的行和它们出现在脚本中的顺序。 记住这个函数 - 或者def翻译会说,如果自己自欺欺人的话:

  • 打开 xy.py 作为“ home” 文件; 调用它"__main__"和在__name__变量。
  • 导入并打开文件__name__ == "ab.py".
  • 哦,一个功能,我会记住的
  • Ok, 函数函数a(); 我刚学到了这一点。打印ab 文件中的函数'.
  • 文件结束; 返回到"__main__"!
  • 哦,一个功能,我会记住的
  • 再来一个
  • 函数职能职能职能职能职能职能职能职能x(); OK, 打印 '外围任务:在其他项目中可能有用'.
  • 这是什么?if条件已经满足(变量__name__设定为"__main__"),所以我将进入main()函数和打印main 函数:这是动作所在位置'.

底下两行的意思是: "如果这是"__main__"或“ home” 脚本, 执行调用的函数main()这就是为什么你会看到def main():上方块块, 包含脚本功能的主流 。

为什么要执行这一规定?

还记得我之前说过的进口对帐单吗 ? 当您导入一个模块时, 它不只是“ 承认” 它, 等待进一步的指示 - 它实际上运行脚本中包含的所有可执行操作 。 所以, 将您的脚本中的肉输入到脚本中 。main()功能有效隔离它, 将其隔离, 这样它不会在被其它脚本导入时立即运行 。

同样,也有例外,但通常的做法是:main()通常不会在外部被调用。所以你可能想知道一件事: 如果我们不打电话,main(), 为什么我们要调用剧本? 这是因为许多人用独立的功能构建剧本结构, 这些功能是用来独立运行的, 独立于文件的其余代码。 他们后来在剧本的正文中被调用到别的地方。 这让我想到:

但是没有它 代码是有效的

是的,没错,这些独立的功能能够被调自一个内线脚本, 它不包含在main()函数。如果您习惯(像我一样,在编程的早期学习阶段) 建立内部脚本, 来做你需要的, 你会试着再弄清楚, 如果你需要操作的话... 好吧, 你对代码的这种内部结构并不习惯, 因为它更复杂, 并且没有直观的阅读能力。

但是,这个剧本可能无法将其功能外部命名, 因为如果它真的存在的话, 它会立即开始计算和分配变量。如果你试图重新使用一个函数, 你的新剧本就会与旧剧本紧密相连, 而旧剧本会互相冲突。

分离独立函数时, 您可以通过将您先前的作品调用为另一个脚本来重新使用您之前的工作 。 例如, “ example. py” 可能会导入“ Xy. py” 并调用x(),使用“xy.py”中的“x”函数(也许它正在将给定文本字符串的第三个字数化为资本化;从数字列表中创建 NumPy 阵列并进行排列;或解开3D表面。可能性是无限的。)

(以物配主者,问题 本问题@ kindall 的回答, 终于帮助我理解为什么, 而不是如何。 不幸的是, 它被标记为重复这个我认为这是一个错误。 )

在解释之前if __name__ == '__main__'了解什么是__name__和它的作用。

什么是__name__?

__name__是 a 是达德阿里亚斯Name- 可被视为全球变量(可从模块中获取),工作方式与global.

它是一个字符串(如上所述,全球范围),如下文所示:type(__name__)(年均(年均)<class 'str'>),而两者都是一个内在的标准,Python 3Python 2版本的版本 。

何处处

它不仅可以用于脚本,还可以在口译和模块/软件包中找到。

解释器 :

>>> print(__name__)
__main__
>>>

脚本 :

测试_ 文件. py:

print(__name__)

导致__main__

模块或包件 :

一些文件. py:

def somefunction():
    print(__name__)

测试_ 文件. py :

import somefile
somefile.somefunction()

导致somefile

请注意,如果在包件或模块中使用,__name__选择文件的名称。没有给实际模块或软件包路径的路径,而是有它自己的 DunderAlias 路径。__file__,允许这样做。

你应该看到,在哪里__name__,它是主文件(或程序)的始终始终返回返回__main__,如果它是模块/软件包,或者正在从其他 Python 脚本中运行的东西,将返回其来源文件的名称。

实践实践实践

变数意味着它的价值能够被覆盖 (“ can” 并不意味着“sh') , 覆盖__name__将会导致缺乏可读性。 所以无论出于什么原因都不要这样做。 如果您需要变量定义新的变量, 请定义新的变量 。

人们总是认为,人们总是认为,__name__待 待 待 待 待 待 待 待__main__或文件的名称。 再次更改此默认值将会造成更多的混乱, 从而导致问题更加严重 。

示例:

>>> __name__ = 'Horrify' # Change default from __main__
>>> if __name__ == 'Horrify': print(__name__)
...
>>> else: print('Not Horrify')
...
Horrify
>>>

一般认为良好做法包括:if __name__ == '__main__'在脚本中。

现在回答if __name__ == '__main__':

现在我们知道__name__(b) 使情况更加明确:

A 音 Aif是一个流量控制语句,其中含有如果给定值是真实的将执行的代码块块。我们已经看到__name__中可选择其中之一__main__或从它导入的文件名 。

这意味着如果__name__等于__main__然后,文件必须是主文件,而且必须实际运行(或翻译),而不是将模块或软件包导入到脚本中。

如果确实__name__值的数值__main__然后那块代码里的任何东西 都会被执行

这告诉我们, 如果正在运行的文件是主文件( 或者您正在直接从翻译器中运行) , 那么该条件必须执行。 如果它是软件包, 那么它不应该, 而值将不会是__main__.

模块模块

__name__也可以用于模块中定义模块名称的模块

变式

此外,还可能采取其他不太常见但有用的措施,包括:__name__有些我会在这里展示:

仅在文件是一个模块或软件包时才执行

if __name__ != '__main__':
    # Do some useful things 

如果文件是主文件,则运行一个条件;如果不是主文件,则运行另一个条件

if __name__ == '__main__':
    # Execute something
else:
    # Do some useful things

您也可以使用它在软件包和模块上提供可运行的帮助功能/用途,而不必精密使用图书馆。

它还允许模块作为主脚本从命令行运行,这也非常有用。