Python學(xué)習(xí)筆記3

數(shù)據(jù)類型(補充) 上一部分

  • 集合
  • 時間日歷

函數(shù)

  • 函數(shù)的參數(shù)
  • 返回值
  • 偏函數(shù)
  • 高階函數(shù)
  • 匿名函數(shù)
  • 閉包
  • 裝飾器
  • 生成器

集合

無序的,不可隨機訪問的不可重復(fù)的元素集合

  • 與數(shù)學(xué)中的集合類似,可以進(jìn)行集合的交、并、差、補等操作。
  • 分為可變集合不可變集合
    • set: 可以進(jìn)行增、刪、改操作
    • frozenset: 創(chuàng)建好之后,無法再做修改。
可變集合的表示
# 直接表示

s = {1, 2, 3, 4}
print(s, type(s))  # {1, 3, 4, 2} <class 'set'>

# set(Iterable)

s1 = set("abc")
s2 = set([1, 2, 3])

print(s1, s2)   # {'a', 'b', 'c'}   {1, 2, 3}

# 集合推導(dǎo)
# 參考列表推導(dǎo)

s = {x for x in range(3)}
print(s)    # {1, 0, 2}
不可變集合
# frozenset(iterable)

fs = frozenset("abc")
print(fs)   # frozenset({'a', 'c', 'b'})

# 集合推導(dǎo)

fs = frozenset(x**2 for x in range(1, 6) if x % 2)
print(fs)   # frozenset({1, 25, 9})
注意事項
  • 創(chuàng)建空集合
    # 錯誤做法
    s = {}    # 實際上構(gòu)建了一個空字典
    
    s = set()     # 空集合
    
  • 集合中的元素必須是可哈希的值(不可變類型)。
  • 集合中元素若出現(xiàn)重復(fù),則會被合并成一個。
    # 多用于給列表元素進(jìn)行去重
    
    li = {1, 2, 2, 3, 3}
    li = list(set(li))
    print(li)     # [1, 2, 3]
    
集合的操作
  • 單集合操作

    s = {1, 2, 3}
    
    #-----------------------------------------
    # 新增元素
    # 1.集合可變  2.新增元素可哈希
    
    s.add(4)
    print(s)  # {1, 3, 2, 4}
    
    #-----------------------------------------
    # 刪除元素
    # 1.remove(element)
    # 刪除指定的元素,若無該元素,報錯
    
    s.remove(2)
    print(s)      # {1, 3}
    
    # 2.discard(element)
    # 刪除指定的元素,若無該元素,pass
    
    s.discard(2)
    print(s)      # {1, 3}
    s.discard(666)
    print(s)      # {1, 3}
    
    # 3.pop(element)
    # 刪除并返回指定元素,若無該元素,報錯
    # 省略 element,不指定刪除元素,進(jìn)行隨機刪除;集合為空,報錯
    
    s.pop(1)
    print(s)      # {2, 3}
    
    s.pop()       
    print(s)      # {2}
    
    s.pop()   
    print(s)      # set()  //空集合的意思
    
    # 4.clear()
    # 清空集合,集合依然存在
    
    s.clear()
    print(s)  # set()
    
    #-----------------------------------------
    # 遍歷集合
    # 1.for in
    
    for v in s:
      print(s, sep=' ')   # 1 2 3
      
    # 2.迭代器
    its = iter(s)
    
    print(next(its))  # 1
    print(next(its))  # 2
    print(next(its))  # 3
    
  • 多集合操作

    • intersection(iterable):

      # 求交集,參數(shù)是可迭代類型
      s1, s2 = {1, 2, 3, 4, 5}, {9, 8, 8, 5, 4}
      
      res = s1.intersection(s2)
      print(res)                  # {4, 5}
      # s1也可以是frozenset,返回結(jié)果也是frozenset
      
      # 可以使用邏輯運算符來完成
      print(s1 & s2)      # {4, 5}
      
    • intersection_update(iterable)

      # 更新調(diào)用該方法的對象
      s1, s2 = {1, 2, 3, 4, 5}, {9, 8, 8, 5, 4}
      s1.intersection_update(s2)
      print(s1)       # {4, 5}
      
    • union(iterable):

      # 求并集,參數(shù)是可迭代類型
      s1, s2 = {1, 2, 3}, {2, 3, 4}
      
      res = s1.union(s2)
      print(res)          # {1, 2, 3, 4}
      
      # 可以使用邏輯運算符來完成
      print(s1 | s2)      # {1, 2, 3, 4}
      
    • update(iterable)

      s1, s2 = {1, 2, 3}, {2, 3, 4}
      s1.update(s2)
      print(s1)       # {1, 2, 3, 4}
      
    • difference(iterable)

      # 求差集
      s1, s2 = {1, 2, 3}, {2, 3, 4}
      res = s1.difference(s2)
      print(res)          # {1}
      
      # 邏輯運算符
      print(s1 - s2)      # {1}
      
    • difference_update(iterable):

      s1, s2 = {1, 2, 3}, {2, 3, 4}
      s1.difference_update(s2)
      print(s1)       # {1}
      
    • 判定操作

      # isdisjoint() 兩個集合是否不相交
      # isuperset()  一個集合是否包含另一個集合
      # issubset()   一個集合是否包含于另一個集合
      

時間日歷

time模塊
  • 獲得當(dāng)前時間戳
    # 獲得從 1970年1月1日到現(xiàn)在的時間秒數(shù)
    
    import time
    t = time.time()
    
    yearSpan = t / (60 * 60 * 24 * 365)
    print(yearSpan)       # 48.6441059296045
    
  • 獲得時間元組
    # 根據(jù)所給的時間戳,返回當(dāng)時的時間信息
    
    import time
    t = time.time()
    
    res = localtime(t)
    print(res)    # time.struct_time(tm_year=2018, tm_mon=8, tm_mday=12, tm_hour=10, tm_min=22, tm_sec=4, tm_wday=6, tm_yday=224, tm_isdst=0)
    
  • 獲得格式化的時間
    # 根據(jù)所給定的時間戳,返回一個更加可讀的時間
    
    import time
    t = time.time()
    
    res = time.ctime(t)
    print(res)        # Sun Aug 12 10:33:58 2018
    
  • 獲得格式化的時間字符串
    # time.strftime(格式字符串, 時間元組)
    
    res = time.strftime("%y-%m-%d %H:%M:%S", time.localtime())
    print(res)    # 18-08-12 10:39:28
    
    res = time.strftime("%Y-%m-%d %H:%M:%S", time.localtime())
    print(res)    # 2018-08-12 10:39:50
    
  • 獲取當(dāng)前cpu時間
    # 常用來統(tǒng)計一段代碼的執(zhí)行時間
    import time
    
    # IDLE環(huán)境測試
    
    start = time.clock()
    for i in range(0, 10)
        print(i, end=' ')
    end = time.clock()
    
    print(end - start)    # 0.02806393769252448
    
  • 休眠
# 線程休眠

# 每隔一秒打印一個數(shù)字
import time

n = 0
while True:
    print(n)
    time.sleep(1)   # 參數(shù)單位是秒
datetiem模塊

模塊內(nèi)部有多個datetime、date、time。使用時選擇合適的類進(jìn)行操作就行了

  • 獲取當(dāng)天的日期
    import datetime
    t = datetime.datetime.now()
    
    print(type(t))    # <class 'datetime.datetime'>
    print(t)          # 2018-08-12 11:04:12.982890
    print(t.year)     # 2018
    print(t.month)    # 8
    
    
  • 計算n天之后的日期
    import datetime
    
    t = datetime.datetime.today()
    res = t + datetime.timedelta(days=7)
    print(t, res, sep='|')    # 2018-08-12 11:10:31.995501|2018-08-19 11:10:31.995501
    
  • 獲得兩個日期的時間差
    import datetime
    
    first = datetime.datetime(2018, 9, 10, 12, 0, 0)
    second = datetime.datetime(2018, 10, 1, 0, 0, 0)
    
    res = second - first
    print(res)    # 20 days, 12:00:00
    

函數(shù)

  • 將一段代碼集中到一塊,起一個名字,下次可以根據(jù)這個名字再次使用這個代碼塊。
  • 作用
    • 方便代碼重用
    • 分解任務(wù),簡化程序邏輯
    • 使代碼更加模塊化
函數(shù)的參數(shù)

所有的傳參方式都是傳引用,注意列表做參數(shù)和數(shù)值做參數(shù)容易出現(xiàn)的問題。

  • 單個參數(shù)

  • 多個參數(shù)

    # 定義方式
    def funName(arg1, arg2, arg3...):
    
    # 調(diào)用方法
    funName(arg1, arg2, arg3...)      # 形參和實參一一對應(yīng)
    funName(arg2=v1, arg3=v3, arg1=v1)    # 指明形參的名稱,不用嚴(yán)格按照順序
    
  • 不定長參數(shù)

    # 1. 利用元組的拆包裝包
    def mySum(*args):
        print(type(args))      # <class 'tuple'>
        print(args)       # (1, 2, 3, 4)
        print(*args)      # 拆包操作 1, 2, 3, 4
        
        for v in args:
            # todo ...
    # 裝包,將傳入的參數(shù)裝入一個元組中,args就成了一個元組對象
    # 拆包,將一個元組中的元素拆分出來,*args就成了參數(shù)序列
            
    # 2. 利用字典的鍵值對
    def myInfo(**args):
        print(type(args))     # <class 'dict'>
        
        # todo ...
    
    myInfo(name="rity", age=12)
    
  • 默認(rèn)參數(shù)

    # 調(diào)用某些函數(shù)時,可以省略某些參數(shù),采用定義時指定的值
    # 若不省略,則以調(diào)用時輸入的為準(zhǔn)
    
    def sorted(iterable, reverse=False):
        # todo...
    
    sorted([1, 3, 2, 5], reverse=True)
    
返回值
  • 返回語句標(biāo)志著函數(shù)的結(jié)束,一個函數(shù)最好只有一處返回語句
  • 如果想返回多個數(shù)據(jù),可以把數(shù)據(jù)包裝成一個集合,整體返回(列表,元組,字典...)
def funName():
    # todo...
    return data
偏函數(shù)
  • 對于一個默認(rèn)值較多的函數(shù),有時我們需要重復(fù)用到其中的部分默認(rèn)值,每次指定默認(rèn)值比較麻煩。
  • 可以將其中的默認(rèn)值先賦值好,然后封裝成一個新的函數(shù),這就是偏函數(shù)。
import functools

numStr = "100010"
res = int(numStr, base=2)
print(res)      # 34

int2 = functools.partial(int, base=2)   # 重新封裝,構(gòu)成偏函數(shù)
print(int2(numStr))     # 34
高階函數(shù)
  • 一個函數(shù)的參數(shù)可以是另外一個函數(shù)
def calculate(a, b, cal_fun):
    print(cal_fun(a, b))

def sum(a, b):
    return a + b
    
def sub(a, b):
    return a - b
    
calculate(2, 3, sum)    # 5
calculate(2, 3, sub)    # -1
匿名函數(shù)
  • lambda表達(dá)式
  • 沒有名字的函數(shù)
res = (lambda x, y : x + y)(1, 2)
print(res)  # 3

fun = lambda x, y : x + y
print(fun(2, 3))    # 5

# 更多的是配合 map(), reduce()等函數(shù)進(jìn)行使用
閉包
  • 在函數(shù)嵌套定義的前提下
  • 內(nèi)層函數(shù)引用了外層函數(shù)的變量
  • 外層函數(shù)把內(nèi)層函數(shù)當(dāng)做返回值
def line_config(content, length):
    
    define line():
        print(content * length)
        
    return line

line1 = line_config("-", 5);
line2 = line_config("*", 6)

line1();    # -----
line2();    # ******
  • 作用域問題:內(nèi)層函數(shù)要修改外層函數(shù)的變量,要使用nonlocal進(jìn)行聲明,否則變量屬于內(nèi)層函數(shù)。
def test():
    num = 10
    
    def test2():
        nonlocal num    # test中的 num被修改
        num = 666
    
    return test2
  • 當(dāng)內(nèi)層函數(shù)使用外層的變化量時,注意值得情況
def test():
    funs = []
    for i in range(1, 4):
    
    def test2():
        print(i)

    funs.append(test2)
    return funs
    
myFuns = test()

myFuns[0]()     # 3     // 函數(shù)在運行時才會去確定變量的值
myFuns[1]()     # 3     // 運行時,索引 i的值已經(jīng)發(fā)生變化了
myFuns[2]()     # 3
裝飾器
  • 在調(diào)用目標(biāo)函數(shù)之前,對這個函數(shù)對象進(jìn)行裝飾(增加一些其他功能)。
  • 函數(shù)的名字不能改變。
  • 函數(shù)體內(nèi)部的代碼不能發(fā)生改變。
def check(func):
    
    def inner():
        print("登錄驗證...")
        func()
    
    return inner()
    
# 在 fss()和 ftp()執(zhí)行之前,都會送入 check()進(jìn)行包裝

@check          
def fss():
    print("發(fā)說說")

# 上面三行等價于 fss = check(fss)

@check
def ftp():
    print("發(fā)圖片")

# 上面三行等價于 ftp = check(ftp)
    
# 主業(yè)務(wù)邏輯如下:

flag = 1
if flag == 1:
    fss()       # 登錄驗證...
else:           # 發(fā)說說
    ftp()
  • 多個裝飾器的調(diào)用順序
def one(func):
    print('----1----')
    def two():
        print('----2----')
        func()
    return two

def a(func):
    print('----a----')
    def b():
        print('----b----')
        func()
    return b

@one
@a
def demo():
    print('----3----')

demo()

# 運行結(jié)果  //從下到上裝飾,從上到下執(zhí)行,分析略
# 裝飾的過程就相當(dāng)于你把一件禮物一層一層的進(jìn)行包裝,先包裝內(nèi)層
# 執(zhí)行的過程就是把禮物拆開,最外面的包裝先被拆開
----a----
----1----
----2----
----b----
----3----
  • 帶有參數(shù)的函數(shù)進(jìn)行裝飾
def zsq(funcs):
    
    def inner(*args, **kwargs):     # 裝包
        print("-" * 5)
        func(*args, **kwargs)       # 拆包
    return inner

@zsq
def fun1(n1, n2, n3):
    print(n1, n2, n3)
    
@zsq
def fun2(n):
    print(n)
    
fun1(1, 2, n3=8)    # 1 2 8
fun2(3)     # 3
  • 對帶有返回值的函數(shù)進(jìn)行裝飾
def zsq(funcs):
    
    def inner(*args, **kwargs):     # 裝包
        print("-" * 5)
        res = func(*args, **kwargs)       # 拆包
    return res
    
@zsq
def fun1(n1, n2, n3):
    return sum(n1, n2, n3)

fun1(1, 2, 3)
  • 帶有參數(shù)的裝飾器
def getzsq(char):

    def zsq (func):
    
        def inner():
            print(char * 5)
            func()
        
        return inner
    
    return zsq
    
@getzsq("*")
def f():            # *****
    print("666")    # 666
    
@getzsq("-")
def f1():           # -----
    print("666")    # 666
生成器
  • 是一個特殊的迭代器
  • 特性:
    • 惰性計算數(shù)據(jù),節(jié)省內(nèi)存
    • 能夠記錄狀態(tài),通過next()函數(shù),訪問下一個狀態(tài)
  • 使用方式
# 生成器表達(dá)式
l = (i for i in range(1, 10000000) if i % 2)
print(type(l))        # <class 'generator'> // 不是元組推導(dǎo),沒有元組推導(dǎo)式

print(next(l))      # 1
print(next(l))      # 3

for i in l:
    print(i)        # 循環(huán)打印出所有滿足條件的值
    
# 生成器函數(shù)
def test():
    for i in range(1, 9):
        yield i

g = test()
print(next(g))      # 1
print(next(g))      # 2
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

  • 寫在前面的話 代碼中的# > 表示的是輸出結(jié)果 輸入 使用input()函數(shù) 用法 注意input函數(shù)輸出的均是字...
    FlyingLittlePG閱讀 3,202評論 0 9
  • 那么大的太陽下面路遇一位母親帶著一個和我女兒差不多大的小女孩兒,遠(yuǎn)遠(yuǎn)的看到她們一前一后的走著,這個畫面打動了我,決...
    隱世閑人閱讀 441評論 4 5
  • 1月15日一個普通的日子,于我卻很特別,因為我生于35年前的這一天。 生日過到35歲,其實也沒什么新意了,今天偶然...
    白珍珠閱讀 465評論 0 4
  • 文|峰語 有人問我 什么緣 我在路上多走了一會 就多看到了幾個人
    代峰語閱讀 170評論 2 7

友情鏈接更多精彩內(nèi)容