<button id="2ddn7"><acronym id="2ddn7"></acronym></button>

<button id="2ddn7"><acronym id="2ddn7"></acronym></button>

  • <button id="2ddn7"><object id="2ddn7"></object></button>
      1. <s id="2ddn7"></s>
        更多課程 選擇中心


        Python培訓

        400-111-8989

        Python 學習筆記-表達式-運算符

        • 發布:雨痕
        • 來源:雨痕學堂
        • 時間:2017-08-11 15:12

        示例運行環境: CPython 3.6.1, macOS 10.12.5

        鑒于不同運行環境差異,示例輸出結果會有所不同。尤其是 id,以及內存地址等信息。 請以實際運行結果為準。

        運算符

        相比其他語言,Python 運算符更接近自然表達方式。也正因如此,優先級導致的錯誤更加隱蔽,不易察覺和排除。

        看下面示例,即便用括號調整優先級,也很難發現是否存在缺陷。

        >>> not "a" in ["a", 1] # 誰先誰后 ?False>>> (not "a") in ["a", 1] # not 先 ?False>>> not ("a" in ["a", 1]) # in 先 ? 看不出來。False

        可一旦數據變化,其結果就可能不同。除非測試數據完整覆蓋,否則導致帶病上線。

        >>> not "a" in [1]True>>> (not "a") in [1]False>>> not ("a" in [1])True

        該示例也提示我們,適當使用括號,不但可避免隱蔽錯誤,還能提高代碼可讀性。


        每個運算符都有對應函數 (方法) 實現,可像普通函數那樣作為邏輯傳遞。當然,用動態執行也未嘗不可。

        def calc(x, y, op): return op(x, y)

        >>> import operator>>> calc(1, 2, operator.add)3>>> calc(1, 2, operator.mul)2

        不僅僅是數學運算符,operator 還有 itemgetter、attrgetter 等用于索引和成員訪問函數。

        除此之外,還可用標準庫提供的輔助函數,簡化自定義類型運算符重載代碼。

        使用 functools.total_order 裝飾器,基于 __eq__、__lt__ 方法,補全剩余比較方法。

        @functools.total_orderingclass X: def __init__(self, n): self.n = n def __eq__(self, o): return self.n == o.n def __lt__(self, o): return self.n < o.n

        >>> a, b = X(1), X(2)>>> a <= bTrue>>> a >= bFalse

        Python 3 對運算符做了些調整。

        移除 “<>”,統一使用 “!=” 運算符。

        移除 cmp 函數,自行重載相關運算符方法。

        除法 “/” 表示 True Division,總是返回浮點數。

        不再支持反引號 repr 操作,調用同名函數。

        不再支持非數字類型混合比較,可自定義相關方法。

        不再支持字典相等以外的比較操作。

        鏈式比較

        鏈式比較(chained comparison)將多個比較表達式組合到一起,更符合人類閱讀習慣, 而非面向機器。該方式可有效縮短代碼,并稍稍提升性能。

        >>> a, b = 2, 3>>> a > 0 and b > a and b <= 5True>>> 0 < a < b <= 5 # 可讀性好,更易維護。True

        反匯編查看兩者差異。

        >>> dis.dis(compile("1 < a and a < 2", "", "eval"))1

        0 LOAD_CONST 0 (1) 2 LOAD_NAME 0 (a) # 載入。 4 DUP_TOP # 直接復制。 6 ROT_THREE 8 COMPARE_OP 0 (<) 10 JUMP_IF_FALSE_OR_POP 18 12 LOAD_CONST 1 (2) 14 COMPARE_OP 0 (<) 16 RETURN_VALUE >> 18 ROT_TWO 20 POP_TOP 22 RETURN_VALUE

        顯然,鏈式比較減少了載入指令,更多基于棧數據復制和交換。僅憑這點,其執行性能就有所提高。但整體上看,這點改善遠不如代碼可讀性和可維護性吸引人。

        切片

        切片(slice)用以表達序列對象的某個片段(或整體),其具體行為與其在出現在語句中的位置有關。當以右值出現時,復制序列數據;而左值則表達要操控的目標范圍。

        >>> x = [0, 1, 2, 3, 4, 5, 6]>>> s = x[2:5] # 從列表中復制指定范圍的引用。>>> s[2, 3, 4]

        >>> x.insert(3, 100) # 對原列表的修改,不影響切片。>>> x[0, 1, 2, 100, 3, 4, 5, 6]>>> s[2, 3, 4]

        注意,列表存儲的是元素對象引用(指針),那么復制的自然也是引用,而非元素對象。切片所 返回新列表與原列表除共享部分元素對象外,其他毫無干系。

        完整的切片操作由三個參數構成。

        以起始和結束索引構成一個半開半閉區間(不含結束位置)。默認起始位置為 0,結束位置 len(x),以容納最后一個元素。

        >>> x = [100, 101, 102, 103, 104, 105, 106]>>> x[2:5:1][102, 103, 104]

        >>> x[:5] # 省略起始索引。[100, 101, 102, 103, 104]>>> x[2:] # 省略結束索引。[102, 103, 104, 105, 106]>>> x[:] # 完整復制。[100, 101, 102, 103, 104, 105, 106]

        可指定步進幅度,間隔選取元素。甚至可以是負值,從右至左反向行進。

        索引 0 表示正向第一元素,所以反向索引從 -1 起始。

        >>> x[2:6:2][102, 104]>>> x[::2][100, 102, 104, 106]>>> x[::-1] # 反向步進,全部復制。[106, 105, 104, 103, 102, 101, 100]>>> x[5:2:-1] # 反向步進,使用正索引表示起始、結束位置。[105, 104, 103]>>> x[-2:-5:-1] [105, 104, 103]

        除表達式外,也可使用 itertools.islice 函數執行切片操作。

        事實上,負索引不僅用于切片,也可直接訪問序列元素。

        >>> (0, 1, 2)[-2]1>>> "abcd"[-3]'b'

        刪除

        用切片指定要刪除的序列范圍。

        >>> x = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]>>> del x[3:7]>>> x[0, 1, 2, 7, 8, 9]

        >>> x = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]>>> del x[3:7:2] # 步進刪除。>>> x[0, 1, 2, 4, 6, 7, 8, 9]

        賦值

        以切片方式進行序列局部賦值,相當于先刪除,后插入。

        >>> x = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]>>> x[3:7] = [100, 200]>>> x[0, 1, 2, 100, 200, 7, 8, 9]

        如設定步進,則刪除和插入元素數量必須相等。

        >>> x = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]>>> x[::2] # 查看要刪除的元素。[0, 2, 4, 6, 8]>>> x[::2] = [100, 200, 400, 600, 800] # 步進插入。>>> x[100, 1, 200, 3, 400, 5, 600, 7, 800, 9]

        >>> x[::2] = [0, 2, 4]ValueError: attempt to assign sequence of size 3 to extended slice of size 5>>> x[::2] = [0, 2, 4, 6, 8, 10]ValueError: attempt to assign sequence of size 6 to extended slice of size 5

        邏輯運算

        邏輯運算用于判斷多個條件的布爾結果,或返回有效操作數。

        分別以 and、or、not 運算符表示邏輯與、或、非三種關系。 其中 and 返回最后,或導致短路的操作數;or 返回第一真值,或最后操作數。

        >>> 1 and 2 # 最后操作數。2>>> 1 and 0 and 2 # 導致短路的操作數。0

        >>> 1 or 0 # 第一真值。1>>> 0 or 1 or 2 # 第一真值。1>>> 0 or [] # 最后操作數。[]

        相同邏輯運算符一旦短路,后續計算被終止。

        def x(o): # 輸出執行信息。 print("op:", o) return o

        >>> x(0) and x(1) # 0 導致短路。op: 00>>> x(1) or x(2) # 返回 1 真值,短路。op: 11

        用反匯編可以看得更清楚些。

        >>> dis.dis(compile("0 and 1 and 2 and 3", "", "eval"))1 0 LOAD_CONST 0 (0) 2 JUMP_IF_FALSE_OR_POP 14 # 如果為 False,跳轉到 14。 4 LOAD_CONST 1 (1) 6 JUMP_IF_FALSE_OR_POP 14 8 LOAD_CONST 2 (2) 10 JUMP_IF_FALSE_OR_POP 14 12 LOAD_CONST 3 (3) >> 14 RETURN_VALUE

        >>> dis.dis(compile("1 or 2 or 3 or 4", "", "eval")) 1 0 LOAD_CONST 0 (1) 2 JUMP_IF_TRUE_OR_POP 14 4 LOAD_CONST 1 (2) 6 JUMP_IF_TRUE_OR_POP 14 8 LOAD_CONST 2 (3) 10 JUMP_IF_TRUE_OR_POP 14 12 LOAD_CONST 3 (4) >> 14 RETURN_VALUE

        當然,不同運算符需多次計算。

        >>> x(0) and x(1) or x(2)op: 0op: 22

        >>> dis.dis(compile("0 and 1 and 2 or 9", "", "eval"))1 0 LOAD_CONST 0 (0) 2 POP_JUMP_IF_FALSE 12 # 如果 False,跳轉到 12。 4 LOAD_CONST 1 (1) 6 POP_JUMP_IF_FALSE 12 8 LOAD_CONST 2 (2) 10 JUMP_IF_TRUE_OR_POP 14 >> 12 LOAD_CONST 3 (9) >> 14 RETURN_VALUE

        條件表達式

        另一常見邏輯運算是條件表達式(conditional expression),類似功能在其他語言被稱作三元運算符(ternary operator)。

        T if X else F :當條件 X 為真時,返回 T,否則返回 F。等同 X ? T : F。

        >>> "T" if 2 > 1 else "F" # 等同 2 > 1 ? T : F'T'>>> "T" if 2 < 1 else "F"'F'

        也可用邏輯運算符實現同等效果,且方式更接近傳統習慣。

        >>> 2 > 1 and "T" or "F" # 2 > 1 ? T : F'T'>>> 2 < 1 and "T" or "F"'F'

        分解執行步驟,這很容易理解。

        >>> 2 < 1 and "T" or "F"'F'>>> 2 < 1 and "T" # ① 2 < 1 導致短路 。False>>> False or "F" # ② 返回真值 F。'F'

        可惜此方法存在缺陷:當 T 為假時,那么 or 必然返回最后操作數,與預期不符。

        >>> 2 > 1 and "" or "F"'F'>>> 2 > 1 and "" # ① 返回最后操作數 ""。''>>> "" or "F" # ② 返回真值 F,與期望值 "" 不符。'F'

        顯然,當 T 和 F 是動態數據時,條件表達式更安全一些。

        >>> "" if 2 > 1 else "F"''

        邏輯運算符還常被用來簡化默認值設置。

        >>> x = None>>> y = x or 100>>> y100

        >>> x = None>>> y = x and x * 2 or 100>>> y100

        預約申請免費試聽課

        填寫下面表單即可預約申請免費試聽!怕錢不夠?可就業掙錢后再付學費! 怕學不會?助教全程陪讀,隨時解惑!擔心就業?一地學習,可全國推薦就業!

        上一篇:Python數據分析入門指南教程
        下一篇:Python學習書籍推薦:Python與機器學習實戰

        Python中類的屬性有哪幾種

        Python語法你知道多少

        Python 中常見的配置文件寫法

        Python爬蟲可以做什么

        • 掃碼領取資料

          回復關鍵字:視頻資料

          免費領取 達內課程視頻學習資料

        • 視頻學習QQ群

          添加QQ群:1143617948

          免費領取達內課程視頻學習資料

        Copyright ? 2021 Tedu.cn All Rights Reserved 京ICP備08000853號-56 京公網安備 11010802029508號 達內時代科技集團有限公司 版權所有

        選擇城市和中心
        黑龍江省

        吉林省

        河北省

        湖南省

        貴州省

        云南省

        廣西省

        海南省

        青青青草网站免费观看|青青青视频在线观看 超真实强奷视频在线看 百度 好搜 搜狗
        <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <蜘蛛词>| <文本链> <文本链> <文本链> <文本链> <文本链> <文本链>