閉包,裝飾器

2022-05-29 23:03:11 字數 3837 閱讀 4673

#

def f1(b):

#def f2():

#print(b)

#f2()##

f1()

#閉包的定義

#內部的函式引用了外部函式的變數

#def f1(b): #

閉包的常用狀態

deff2():

print

(b)

return

f2f2 = f1('

bbb'

)ff = f1('

bbb'

)ff()

#==f1('bbb')()

#def f1(): #從內部函式返回乙個值到全域性

#b = 10

#def f2():

#return b

#return f2()

#print(f1())#爬蟲

from urllib.request import

urlopen

#ret = urlopen('').read()

#print(ret)

defget_url(url):

defread1():

ret =urlopen(url).read()

print

(ret)

return

read1

read_func = get_url('

')read_func()

read_func()

#

#講故事

##帶著你一步一步的剖析裝飾器的成因

#import time #模組#

start_time = time.time()

#time.sleep(1) # 睡眠時間

#end_time = time.time()

#print('*****%s*****'%(end_time-start_time))

import time #

模組def

timmer(func):

definner():

start_time =time.time()

time.sleep(0.1)

func()

end_time =time.time()

print('

*****%s*****

' % (end_time -start_time))

return

inner

deffunc():

print('

公司好老闆好同事好')

func =timmer(func)

func()##

裝飾器的作用

#在不改變函式的呼叫方式的情況下,給函式的前後新增新的功能##

從最簡單的裝飾器

def timmer(qqxing): #

timmer是裝飾器的名字,傳入的引數就是被裝飾的函式

def inner(): #

在裝飾器中需要定義乙個內部函式

print('

努力工作')

qqxing()

#被裝飾的函式,並且要執行 功能模組

print('

吃喝玩樂')

return inner #

將內部函式的名字返回

@timmer

#語法糖 func = timmer(func)功能模組

deffunc():

print('有錢'

)func()

## 完整的裝飾-萬能的裝飾

#def timmer(qqxing): #timmer是裝飾器的名字,傳入的引數就是被裝飾的函式

#def inner(*args,**kwargs): #在裝飾器中需要定義乙個內部函式

#print('呼叫func之前')

#ret = qqxing(*args,**kwargs) #被裝飾的函式,並且要執行

#print('呼叫func之後')

#return ret

#return inner #將內部函式的名字返回##

@timmer #語法糖 func = timmer(func)

#def func(name):

#print('%s的公司好老闆好同事好'%(name))

#return 1111111111##

ret = func('俊傑')

#print('result : %s'%ret)##

#裝飾器的固定結構##

def inner(*args,**kwargs):

#"""被裝飾函式執行之前要新增的**"""

#ret = func(*args,**kwargs)

#"""被裝飾函式執行之後要新增的**"""

#return ret

#return inner##

##

作業

1.編寫裝飾器,為多個函式加上認證的功能(使用者的賬號密碼**於檔案),要求登入成功一次,後續的函式都無需再輸入使用者名稱和密碼
login_dic = 

deflogin(func):

def inner(*args,**kwargs):

ifnot login_dic['

alex']:

usrname = input('

使用者名稱 : ')

passwd = input('

密 碼 : ')

with open(

'userinfo

') as f:

for line in

f: usr,pwd = line.split('')

if usrname.strip() == usr and passwd.strip() ==pwd:

print('

登陸成功')

login_dic[usrname] =true

if login_dic['

alex']:

ret = func(*args,**kwargs)

return

ret

return

inner

@login

defhome():

print('

歡迎來到home頁')

home()

home()

home()

2.編寫裝飾器,為多個函式加上記錄呼叫功能,要求每次呼叫函式都將被呼叫的函式名稱寫入檔案
def

log(func):

def inner(*args,**kwargs):

with open(

'func.log

','a+

',encoding='

utf-8

') as f:

f.write(

'%s被呼叫了\n

'%func.__name__

) ret = func(*args,**kwargs)

return

ret

return

inner

@log

deffunc1():

print('

我是func1')

@log

deffunc2():

print('

我是func2')

func1()

func1()

func2()

閉包 裝飾器

外部函式返回內部函式的引用 內部函式可以直接使用外部函式的環境變數 語法 外部函式通過返回內部函式的引用 內部函式可以直接使用外部函式的 環境變數 自由變數 函式執行時間統計 執行函式前預備處理 執行函式後清理功能 許可權校驗等場景 快取有且只有乙個引數 指向了被裝飾的函式的引用 使用裝飾器 裝飾器...

閉包,裝飾器

多層函式巢狀,函式裡面還有定義函式,一般是兩個 往往內層函式會用到外層函式的變數,把內層函式以及外部函式的變數當成乙個特殊的物件,這就是閉包。閉包比物件導向更純淨 更輕量,既有資料又有執行資料的 比普通函式功能更強大,不僅有 還有資料 利用閉包的基本原理,對乙個目標函式進行裝飾,即在執行乙個目標函式...

閉包 裝飾器

定義乙個函式 def test number 在函式內部再定義乙個函式,並且這個函式用到了外邊函式的變數,那麼將這個函式及用到的一些變數稱之為閉包 def test in number in print in text in 函式,number in is d number in return nu...