闭包函数
闭包指的是函数内部的函数对外部作用域而非全局作用域的引用
def outter():
x = 1
def inner():
print(x)
return inner
f = outter()
def f2():
x = 2
f()
f2() #1
两种位函数传参的方式
1.使用参数的形式
def func(x):
print(x)
func(1) #1
func(1) #1
func(1) #1
2.包给函数
def outter(x):
def inner():
print(x)
return inner
f = outter(1)
f()
f()
f()
闭包函数的应用
闭包的意义:返回的函数对象不仅是一个函数对象,在该函数外还包裹了一层作用域,这使得该函数无论在何处调用优先使用自己外层包裹的作用域
import requests
def outter(url):
def get():
response = requests.get(url)
print(f"done: {url}")
return get
baidu=outter('https://www.baidu.com')
python = outter('https://www.python.org')
baidu()
baidu()
python()
python()
装饰器
什么是装饰器
装饰器本质也是一个函数,该函数的功能是位其他函数添加额外的功能,需要注意的是装饰器本身也是可以任意调用的对象,被装饰的对象也是任意可调用的对象
为什么要用装饰器
如果我们要修改一个已上线的项目的方法或者增加功能,但是我们又不想改变方法的使用方法,我们就可以用装饰器来实现。
装饰器的实现必须遵循两大原则:
- 不修改被装饰对象的源代码
- 不修改被装饰对象的调用方式
装饰器模板
def deco(func):
def wrapper(*args,**kwargs):
res = func(*args,**kwargs)
return res
return wrapper
##给音乐专区和电影专区加上登陆验证功能,但是不能改变原来的调用方式
status=False
def login(func):
def inner(*args,**kwargs):
username='alex' #假设是数据库存储的用户信息
password='alex123'
global status
if status==False:
user = input('user:')
pwd = input('password:')
if user==username and pwd==password:
print('-----welcome-----')
status=True #登陆之后修改状态
else:
print('wrong user or password')
else:
print('用户已通过验证登陆')
func(*args,**kwargs)
return inner
@login
def music():
print('-----音乐专区-----')
@login
def movie():
print('-----电影专区-----')
def zongyi():
print('-----综艺专区-----')
# movie=login(movie)
# music=login(music)
movie() #需要先登陆才能进入
music()
zongyi() #直接进去综艺专区
三层装饰器登陆验证还可以限定登陆方式
user_status=False #用户登陆了就把这个改成True
def login(auth_type):
def outer(func):
def inner(*args,**kwargs):
if auth_type=='qq':
_username='alex' #假设是数据库里存储的用户信息
_password='alex123' #假设是数据库里存储的用户信息
global user_status
if user_status==False:
username=input('user: ')
password=input('password:')
if username==_username and password==_password:
print('welcome login')
user_status = True
else:
print('wrong username or password')
else:
print('用户已登陆,验证通过')
if user_status:
return func(*args,**kwargs)
else:
print('只支持qq登陆')
return inner
return outer
def home():
print('-----首页-----')
# @login('qq')
def america():
print('----- 欧美-----')
def japan():
print('----- 日韩-----')
@login('qq') # henan=login(henan) #inner
def henan(style):
print('----- 河南-----',style)
# xx=login('qq')# outer
# print(xx)
# henan=xx(henan)
# print(henan)
america=login('qq')(america)
henan('3p')
america()