wsfking 发表于 2021-8-9 17:12:56

50讲 循环问题第五题记录

# a.py
import b

def x():
print('x')

# b.py
import a

def y():
    print('y')

a.x()

---------------
①发现问题
若没有 if __name__=='__main__': 这一句的话,执行过程如下
执行b.py -> import a -> 查找 a 模块 -> 未发现 a 模块对象(即还未导入过a模块) -> 导入 a.py -> import b -> 查找 b 模块 -> 发现 b 模块对象 -> 接着上次执行的位置往下执行字节码(import a 已执行过,Python 有机制确保不重复导入,因而不会再执行) -> 导入def y() -> 执行 a.x() -> 在 a 模块中找不到 x(),因为 a 还没有被完全导入(因为导入a模块后直接导入b模块,没有对a模块进行初始化(__init__),所以说没有导入完全)。

②解决办法
使用 if __name__ == "__main__" 来确保 Python 不要在导入的过程中调用不该调用的函数。
# a.py
import b   ②导入b模块后才继续以下操作,即④后面的操作          |
                                                                                          |
def x():      ⑤                                                                          |
    print('x')                                                                          |
                                                                                          |
if __name__ == "__main__":⑥不执行                                    |                                                                                                                
    b.y()                                                                                  |

# b.py                                                                                 
import a   ①                                                                        |⑦(①) 继续执行b模块,这时接上了第一个箭头后面的import a
                                                                                          |⑧
def y():       ③(import a已执行过,②-③不再执行)                          |
    print('y')                                                                           |
                                                                                          |⑨此时name=a,执行
if __name__ == "__main__":    ④不执行                                  |
    a.x()

若有if __name__=='__main__': 这一句的话,执行过程如下:
执行b.py -> import a -> 查找 a 模块 -> 未发现 a 模块对象 -> 导入 a.py -> import b -> 查找 b 模块 -> 发现 b 模块对象 -> 接着上次执行的位置往下执行字节码(import a 已执行过,Python 有机制确保不重复导入,因而不会再执行) -> 导入def y() -> 判断if __name__=='__main__' 发现__name__ == 'b',不执行下一句a.x(),b模块导入完成-> 继续导入a模块,接着上次执行的位置往下执行字节码(import b 已执行过)-> 导入def x() -> 判断if __name__=='__main__' 发现__name__ == 'a',不执行下一句b.y(),a模块导入完成-> 继续执行b模块,这时接上了第一个箭头后面的import a,然后定义 def y() (这里实际上是又定义了一遍该函数)-> 判断if __name__=='__main__' 发现__name__ == '__main__',执行下一句a.x()。

执行结构图:
①inport a
        ②import b
                ③
                ④
                ⑤
                ⑥
        ⑧
        ⑨
页: [1]
查看完整版本: 50讲 循环问题第五题记录