邁向大神day13 脫稿一期 生成器的進階
g=generator() #呼叫生成器 list(g) 從生成器中取值的集中方法
- next
- for
- 資料型別的強制裝換 全部取完 佔記憶體
回顧:
迭代器和生成器 迭代器: 雙下方法 : 很少直接呼叫的方法。一般情況下,是通過其他語法觸發的 可迭代的 —— 可迭代協議 含有__iter__的方法('__iter__' in dir(資料)) 可迭代的一定可以被for迴圈 迭代器協議: 含有__iter__和__next__方法 迭代器一定可迭代,可迭代的通過呼叫iter()方法就能得到一個迭代器 迭代器的特點: 很方便使用,且只能取所有的資料取一次 節省記憶體空間 生成器 生成器的本質就是迭代器 生成器的表現形式 生成器函式 生成器表示式 生成器函式: 含有yield關鍵字的函式就是生成器函式 特點: 呼叫函式的之後函式不執行,返回一個生成器 每次呼叫next方法的時候會取到一個值 直到取完最後一個,在執行next會報錯 寫生成器實現:有一個檔案,從檔案裡分段讀取內容 readline read(10) 在讀出來的內容前面加上一個'***',再返回給呼叫者 def generator(): for i in range(20): yield '哇哈哈%s'%i g = generator() 呼叫生成器函式得到一個生成器 print(list(g)) ret = g.__next__() 每一次執行g.__next__就是從生成器中取值,預示著生成器函式中的程式碼繼續執行 print(ret) num = 0 for i in g: num += 1 if num > 50: break print(i)
今日 進階版 優化
def gen():
print(123)
yield 1
print(456)
yield 2
g=gen()
ret=g.__next__()
print("***",ret)
ret=g.__next__()
print("***",ret)
ret=g.__next__()
優化二
def gen():
print(123)
yield 1
print(456)
yield 2
g=gen()
ret=g.__next__()
print("***",ret)
ret=g.send('hello' )
print("***",ret)
優化3 的作用
def gen():
print(123)
con=yield 1
print("======",con)
print(456)
yield 2
g=gen()
ret=g.__next__()
print("***",ret)
ret=g.send('hello') #返回 傳值
print("***",ret)
send 獲取下一個的值的效果和 next 基本一致
只是在獲取下一個值的時候 給上一個yield的位置 傳遞一個數據
!!第一次使用生成器的時候,必須使用next 獲取下一個值
!!最後一個yield不能接受 外部的值
解決最後一個yield的方法
def gen():
print(123)
con=yield 1
print("======",con)
print(456)
res= yield 2
yield
g=gen()
ret=g.__next__()
print("***",ret)
ret=g.send('hello') #返回 傳值
print("***",ret)
獲取移動中平均值
def avg(): ##只能執行一次
sum=0
count=0
avg=0
num=yiel
sum+=num
count+=1
av=sum/c
yield av
av=avg()
av.__next__(
avg1=av.send
print(avg1)
嘿嘿::
更改執行多次
def avg():
sum=0
count=0
avg=0
num=yiel
sum+=num
count+=1
av=sum/c
yield av
av=avg()
av.__next__(
avg1=av.send
print(avg1)
再次優化
def avg():
sum=0
count=0
avg=0
while True:
num=yield
sum+=num
count+=1
avg=sum/c
av=avg()
av.__next__()
avg1=av.send(10)
avg1=av.send(10)
print(avg1)
生成器 yield from 輸出每個字元
python 2
def gen():
a='abcdf'
b='123456'
for i in a:
yield i
for i in b:
yield i
b=gen()
for i in b:
print(i)
python 3的新特性
def gen():
a='abcdf'
b='123456'
yield from a ##new
yield from b
b=gen()
for i in b:
print(i)
生成器表示式和 列表表示式
#格式 for 迴圈 [ i for i range(11)] print(egg_list) ######x效果一樣的
egg_list=[] ###
for i in range(10)
egg_list.append('雞蛋%s'%i)
print(egg_list)
'______________________________________________________'
egg_list=['雞蛋%s'%i for i in range(10)] #列表推倒式
生成器表示式
g=(i for i in range(10)) #生成器表示式 print(g) for i in g: print(i) #括號不一樣 返回值不一樣 ===幾乎不佔用記憶體 (生成器表示式的優點)
egg_list=[‘雞蛋%s’%i for i in range(10)] ##三元運算子 簡化版
推倒式: 遍歷和篩選
[滿足條件的元素相關的操作 for 元素 in 可迭代資料型別 if 元素相關的條件] #篩選器
-
30之內能被三整除的數 res=[for i in range(30) if i%3==0]
-
找到巢狀列表中名字含有兩個‘e’的所有名字·
names=[[‘tony’,‘sony’],[‘tim’][‘thomas’]] #男女分開
ton=[name for list in names for name in list if name.count(‘e’)==2]
字典推倒式
- 字典顛倒 mc={‘a’:10, ‘b’:34}#want {10:‘a’,34:‘b’}
mc1={ mc[k]:k for k in mc} print(mc1)
- 合併大小寫對應的value值 將k 統一成小寫
mc={'A':10,'b':34,'c':54,'a':7} {'a':17}
mcase_frequency = {k.lower(): mcase.get(k.lower(), 0) + mcase.get(k.upper(), 0) for k in mcase}
print(mcase_frequency)
print(d.get(‘g’,0)) # 字典 get 不到的話返回提攻的預設值0
集合推倒式 自帶去重複的 squ={x**2 for x in [1,-1,2]} print(squ)
惰性運算