if __name__ == "__main__":

工欲善其事,必先利其器
# 环境:Python3.6 + win10
# 目录结构:
D:\test\        # 目录
    ├─ t1.py    # 文件
    └─ t2.py    # 文件

让模块如脚本一样运行

在Python中,可以说,每一个py文件都可以说是一个模块,那么每一个模块不仅仅能被调用,也要负责本身的逻辑,如我们在模块t1中定义了一个登录函数并实现登录逻辑:

# t1.py
def login(user, pwd):
    if user == '张开' and pwd == '666':
        return 'login successful'
    return 'login error'


user, pwd = input('user: ').strip(), input('pwd: ').strip()
print(login(user, pwd))
t1.py

那么,这个模块在自己使用的时候,肯定没有问题。但是有一天,这个牛逼的模块被别人使用了,在t2中调用了t1的注册功能:

# t1.py
def register():
    user, pwd = input('user: ').strip(), input('pwd: ').strip()
    if user == '张开' and pwd == '666':
        return 1
    return 0


def login(user, pwd):
    if user == '张开' and pwd == '666':
        return 'login successful'
    return 'login error'


user, pwd = input('user: ').strip(), input('pwd: ').strip()
print(login(user, pwd))
被t2.py 调用了的t1.py
# t2.py
import t1
def register():
    if t1.register():
        return 'register successful'
    return 'register error'
print(register())

'''
user: a
pwd: a
login error
user: a
pwd: a
register error
'''
t2.py

那么,在t2模块内部要实现注册的时候,想到t1不是实现了一个注册的功能了吗?我们就要避免重复造轮子,就直接调过来用了,但是问题来了,当我们在调用一个模块的时候,该模块内的代码会先执行一遍,也就是t2模块示例代码最后展示的交互结果。当t2模块内的代码执行到import t1的时候,触发了原本t1模块的执行,t1模块内部代码从上往下执行,就执行到了登录逻辑。等登录逻辑执行完毕,程序回到t2模块继续往下执行。也就执行到了t2内部的注册函数的执行。而t2的注册函数此时又调用了t1模块的注册的函数的执行,等注册逻辑执行完毕,程序往下继续执行——没有代码,程序结束。

由上述示例可以见到,我们在t2模块调用t1模块的时候,只想调用注册函数,并不想触发t1登录逻辑的执行,那么,该怎么办呢?

if __name__ == "__main__":

我们首先看一下模块内自带都有哪些属性:

# t1.py
print(dir())
'''
['__builtins__', '__cached__', '__doc__', '__file__', '__loader__', '__name__', '__package__', '__spec__']
'''

在上述的打印列表内,此时,__name__属性在这里对我们有帮助,那么我们来研究一个__name__属性是什么鬼?

我们先在各自模块内部打印一下__name__属性。

# t1.py
print('module t1.__name__:', __name__, type(__name__))
'''
module t1.__name__: __main__ <class 'str'>
'''
# t2.py
# import t1
print('module t2.__name__: ', __name__, type(__name__))
'''
module t2.__name__:  __main__ <class 'str'>
'''

通过上例可以看到,各模块各自运行的结果一致,__name__属性都返回了一个str类型的__main__结果,你可能说,这没啥啊,扯半天淡就这看这个了?别急,我们放开t2模块的import t1注释再看:

# t1.py
print('module t1.__name__:', __name__, type(__name__))
'''
module t1.__name__: __main__ <class 'str'>
'''
# t2.py
import t1
print('module t2.__name__: ', __name__, type(__name__))
'''
module t1.__name__: t1 <class 'str'>
module t2.__name__:  __main__ <class 'str'>
'''

通过执行t2模块,发现一个有趣的现象,在导入t1的时候,触发了t1模块的执行,但是,看看此时t1的打印是什么,没错,是t1的模块名!而单独运行t1的时候,结果仍不变,还是__main__。

那么,由此可以做些手脚了,我们通过__name__返回不同的字符串(自己调用返回__main__,被调用时返回自己的模块名),来解决上面那个登录逻辑被执行的问题。那么,我们就在t1中加上一句话:

# t1.py
def register():
    user, pwd = input('user: ').strip(), input('pwd: ').strip()
    if user == '张开' and pwd == '666':
        return 1
    return 0


def login(user, pwd):
    if user == '张开' and pwd == '666':
        return 'login successful'
    return 'login error'


if __name__ == '__main__':
    user, pwd = input('user: ').strip(), input('pwd: ').strip()
    print(login(user, pwd))
t1.py
# t2.py
import t1
def register():
    if t1.register():
        return 'register successful'
    return 'register error'
print(register())
'''
user: 张开
pwd: 666
register successful
'''
t2.py

在t1模块中,当__name__属性返回是字符串__main__的时候,这说明是此次执行是t1模块自己被自己调用,那么我们就把想要实现的逻辑放到该if语句内,表明自己调用时执行。

而当别的模块如t2调用t1的时候,__name__属性返回了t1的模块名,那么t1不等于__main__,t1模块内部的if语句也就不会执行。这样就解决了上例中登录的问题。 


that's all

转载于:https://www.cnblogs.com/Neeo/p/9504779.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值