三.函數迭代器,生成器,內置函數

迭代器:     定義:更新換代的過程 每次迭代都必須基於上一次的的結果     器:迭代取值的工具    特色:不依賴索引取值    迭代取值的數據類型:字符串,列表,元組,字典,集合    一,可迭代對象        1,可迭代對象:只有內置有__iter__方法的都叫作可迭代對象        2,是可迭代對象的有: str list tuple dict set            文件對象(執行內置的__iter__以後仍是自己 沒有任何變化)            文件對象自己就是迭代器對象            案例:  res = s.__iter__()  # res = iter(s)                    print(s.__len__())  # 簡化成了len(s)                    res1 = l.__iter__()  # res1 = iter(l)                    res2 = f1.__iter__()  # res2 = iter(f1)            重點:可迭代對象執行內置的__iter__方法獲得就是該對象的迭代器對象    二:迭代器對象        1,內置有__iter__方法        2,內置有__next__方法  (進行取值)        注意:迭代器對象必定是可迭代對象              而可迭代對象不必定是迭代器對象        必須知足1,2 兩個條件纔是迭代器對象            1》生成一個可迭代對象                l = [1,2]                res = l.__iter__()                # 就是把一個可迭代對象用.__iter__()方法生成迭代器對象            2》迭代器取值  調用 __next__()                print(res.__next__())     #  1                # 調用依次取出一個元素(迭代器對象中有幾個元素就能夠調用幾回)                  直到取完,就會報錯StopIteration                  案列:                    f1 = open('xxx.txt','r',encoding='utf-8')                    調用f1內置的__iter__方法                    iter_f = f1.__iter__()                    print(iter_f is f1)    # 判斷iter_f 是否是 f1 ,打印 True 或者 False        重點:1,迭代器對象的取值必須用 __next__()              2,迭代器對象不管執行多少次__iter__方法,獲得的仍是迭代器對象自己                    # print(f1 is f1.__iter__().__iter__().__iter__().__iter__())              3. 迭代器取值的特色: 只能日後依次取值,不能倒着取        **注意:4,可迭代對象轉爲迭代對象用一次 .__iter__() 就可,屢次調用和第一次調用同樣(能夠理解爲初始化)                5,調用一次.__next__()方法只能取出其中一個元素,(列表爲第一個值,字典取出的是key)    總結:        可迭代對象:內置有__iter__方法的        迭代器對象: 既 內置有__iter__ 也內置有__next__方法        迭代取值:優勢:不依賴索引取值                        內存中始終都佔一份空間,不會致使內存溢出                缺點                    1.不可以獲取指定的元素,只能從前日後依次取                    2.取完以後會報StopIteration錯            案例:1,文件取值案列                    (假如文件中有一行內容,若是有n行就調用n次iter_f.__next__()                    f = open('xxx.txt','r',encoding='utf-8')                    iter_f = f.__iter__()                    print(iter_f.__next__())                2,可迭代對象取值(list,dict,set,tuple,str)                    l = [1,2,3,4]                    iter_l = l.__iter__()                    print(iter_l.__next__())    #  1                    l2 = {'name':'jason'}                    iter_l2 = l2.__iter__()                    print(iter_l2.__next__())   #  name                    l3 = (3,'sr',[1,2],{1,'sc'})                    iter_l3 = l3.__iter__()                    print(iter_l3.__next__())       # 3                    print(iter_l3.__next__())       # sr                    print(iter_l3.__next__())       # [1, 2]                    print(iter_l3.__next__())       # {1, 'sc'}    其中的元素是什麼類型,取出來的也是該數據類型    三:for循環的本質:            for i in d:     #  for循環後面的in關鍵 跟的是一個可迭代對象                    1.將in後面的對象調用__iter__轉換成迭代器對象                    2.調用__next__迭代取值                    3.內部有異常捕獲StopIteration,當__next__報這個錯 自動結束循環    四:生成器:            用戶自定義的迭代器,本質就是迭代器                1,函數內有yield關鍵字存在時,函數名加括號不會運行函數體的代碼塊                    而是將它轉變爲生成器,當用.__next__() 方法時纔會走函數體代碼                2,函數體代碼運行遇到yield 就會暫停運行                3,yield後面跟的值就是調用迭代器__next__方法你能獲得的值   ********                4, yield既能夠返回一個值也能夠返回多個值 而且多個值也是按照元組的形式返回                5,yield 支持外界爲其傳參,多個值時 是以元組的形式返回                案列:                    def func():                        print('egon not is dsb')                        yield 'no'                        print('天上飛來一隻猴')                        yield '666'                    g = func()          # 生成器初始化:將函數變成迭代器                    g.__next__()         ##  egon not is dsb                    print(g.__next__())    #天上飛來一隻猴    666                注意:函數體代碼中有 yield,當函數名加括號調用時,                他就是將函數轉變爲了自定義的生成器,並不會當即執行函數體代碼                    案列:                    def func(name):                        print('%s 準備開吃'%name)                        while True:                            food = yield                            print('%s 吃了 %s'%(name,food))                    g = func('egon')                    g.__next__()  # 必須先將代碼運行至yield 纔可以爲其傳值     #egon 準備開吃                    g.send('每天向上')  # 給yield左邊的變量傳參  觸發了__next__方法   # egon 吃了 每天向上                    g.send('好好學習')    #egon 吃了 好好學習                2,生成器表達式:                    res = (i for i in range(1,100000000) if i != 4)  # 生成器表達式                    print(res)                    1,生成器不會主動執行任何一行代碼                    2,必須經過__next__觸發代碼的運行zcf    四:內置函數            divmod  分頁器            print(divmod(101,10)             enumerate 枚舉             exec(s)             eval(s)            eval不支持邏輯代碼            format 三種玩法            {}佔位            {index} 索引            {name} 指名道姓                        isinstance 後面統一改方法判斷對象是否屬於某個數據類型            n = 1            print(type(n))            print(isinstance(n,list))  # 判斷對象是否屬於某個數據類型            l = [0,1,0]            print(all(l))  # 只要有一個爲False就返回False            print(any(l))  # 只要有一個位True就返回True補充:    異常處理:            while True:                try:                    print(iter_d.__next__())                except StopIteration:                    print( ’取完了,沒有了')                    break
相關文章
相關標籤/搜索