高級函數


高級函數

閉包

# 定義:如果在一個內部函數里,對在外部作用域(但不是在全局作用域)的變量進行引用,那么內部函數就被認為是閉包(closure)
# 閉包 = 函數塊+定義函數時的環境,inner就是函數塊,x就是環境,當然這個環境可以有很多,不止一個簡單的x。
def outer():
    x = 10
    def inter():  # x = 10
        print("inter:", id(inter))
   # python解釋器在解釋代碼的時候,會檢測一下函數里面的變量是否引用外部函數變量名,如果有,就不會從內存中清除此變量 print(x) # 等於此時print(10)已經在內存里面,所以直接調用就可以用 return inter # inter就是一個閉包 inter = outer() # outer的返回值是inter,並且賦值給inter,相當於inter可以直接調用,返回的是inter的內存地址, inter()
 1 def outer(x):
 2 
 3     def inter():  # x = 10
 4         print("inter:", id(inter))
 5         y = x
 6         print(y)
 7         print(x * 3) # 即使x是函數參數,因為內部函數引用了此變量名,依然不會被釋放
 8 
 9     return inter  # inter就是一個閉包
10 
11 
12 inter = outer(10)  
13 inter()

 

裝飾器

有這樣一個函數

1 import time
2 
3 
4 def foo():
5     time.sleep(3)
6     print("this foo.....")

 

需求,在不改動foo函數的前提下,計算出這個函數運行了長時間

方式一

1 def show_time(func):
2     start = time.time()
3     func()
4     end = time.time()
5     print(end - start)
6     return show_time
7 
8 # 將foo函數作為變量,傳入show_time函數中,
9 show_time(foo)

 

 

方式二 使用裝飾器方式

 

 1  無參數
 2 import time
 3 def show_time(func):#裝飾函數盡量放在上面
 4     def inner():
 5         start = time.time()
 6         func()# 因為閉包的原因,func參數並沒有被釋放,現在參數傳遞的是foo
 7         end = time.time()
 8         print(end - start)
 9     return inner
10  
11 @show_time    #完全等於foo = show_time(foo)   裝飾哪個函數,就在那個函數之前添加
12 def foo():
13     time.sleep(3)
14     print("this foo.....")
15 
16
   本質 foo = show_time(foo)
17 foo()

 

 

# 普通參數 or 其他參數
def show_time(func):
    def inner(x, y):# 此處
        start = time.time()
        func(x, y)# 此處 不管是 x,*args,**kwargs 都同add參數
        end = time.time()
        print(end - start)

    return inner

@show_time
def add(x, y):
    time.sleep(2)
    print("各種復雜乘...耗時...", x * y)

add(3,6)

 

# 終極參數(裝飾器參數)
# import time
def looger(flag):
    def show_time(func):
        def inner(*x,**y):
            start = time.time()
            func(*x,*y)
            end = time.time()
            print(end - start)
            if flag == True:
                print("日志記錄")
        return inner
    return show_time


@looger(True)#looger加()了,所以執行了looger函數,返回show_time 此時是@show_time,然后add=show_time(add) => add() == inner()
def add(*x,**y):
    sums = 0
    for i in x:
        sums += sums
        print(sums)
    time.sleep(0.5)
add(3)

 

# 多個裝飾器 裝飾器執行順序從下而上,函數執行從上而下
def wrap_one(func):
    print("first one")
    def inner_a():
        print("inner_a")
        func()

    return inner_a


def wrap_two(func):
    print("first two")
    def inner_b():
        print("inner_b")
        func()

    return inner_b


@wrap_one
@wrap_two
def test():
    print("test")

test()

 

 

#有返回值的函數
def show_time(func):
    def inter(x, *args, **kwargs):
        begin_time = time.time()
        res = func(x, *args, **kwargs)# 執行完用變量接收,計算完時間在返回
        end_time = time.time()
        print("時間:%s" % (end_time - begin_time))
        return res  # 處理帶有返回值的函數,別裝飾的有return,裝飾器也必須有return

    return inter


@show_time
def add(x, *args, **kwargs):
    time.sleep(1)
    return "我轉了一圈發現涼了"


add(1, 2, 32134, 345, 345)

 

 

python內置函數

 

官方地址:https://docs.python.org/zh-cn/3/library/functions.html?highlight=built#ascii

 

關於序列化的內置函數 

map函數

# 需求 將列表里面的每個值都平方一下,在生成一個新列表
data_list = [2, 5, 6, 7]

# 方式一 單純的循環 temp
= [] for data in data_list: temp.append(data ** 2) print(temp) # [4, 25, 36, 49] # 方式二 map函數 # 第一個參數是函數,第二個參數是 iterable(可迭代) 對象, # map會循環第二個參數里面的每個值,經過第一個參數的函數處理,保存到迭代器對象中 result = map(lambda x: x ** 2, [1, 2, 3, 4]) print(list(result))#[1, 4, 9, 16]

 

filter函數

# filter函數
# 需求,假設下面的列表是某班的成績,列出大於60 的分數,並且生成新的字典
data_list = [
    {"name":"張三","score":36},
    {"name":"里斯","score":60},
    {"name":"網速","score":59},
    {"name":"小劉","score":80},
    {"name":"王琦","score":90},
    {"name":"啥酒","score":66},
]
# 方式一 單純的循環
temp = []
for data in data_list:
    if data["score"] >= 60:
        temp.append(data)
print(temp)
# [{'name': '里斯', 'score': 60}, {'name': '小劉', 'score': 80}, {'name': '王琦', 'score': 90}, {'name': '啥酒', 'score': 66}]

#  方式二 filter函數
# result = filter(lambda x:x if x["score"]>=60 else False,data_list)
# 結果同上,filter會用函數調用data_list里面的每個值,如果符合條件,將data_list里面的那個值保存到迭代器中
result = filter(lambda x:x["score"]>=60,data_list)
print(list(result))
# [{'name': '里斯', 'score': 60}, {'name': '小劉', 'score': 80}, {'name': '王琦', 'score': 90}, {'name': '啥酒', 'score': 66}]

 

 

 

 
       


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM