Python 中的 else詳解
我們都知道 Python 中else的基本用法是在條件控制語(yǔ)句中的 if...elif...else...,但是 else 還有兩個(gè)其它的用途,一是用于循環(huán)的結(jié)尾,另一個(gè)是用在錯(cuò)誤處理的 try 中。這原本是 Python 的標(biāo)準(zhǔn)語(yǔ)法,但由于和大部分其它編程語(yǔ)言的習(xí)慣不太一樣,致使人們有意或無(wú)意地忽略了這些用法。另外,對(duì)于這些用法是否符合 0×00 The Zen of Python 的原則以及該不該廣泛使用也存在很多爭(zhēng)議。例如在我看到的兩本書(shū)里(Effective Python VS Write Idiomatic Python),兩位作者就分別對(duì)其持有截然不同的態(tài)度。
循環(huán)中的 else
跟在循環(huán)后面的 else 語(yǔ)句只有在當(dāng)循環(huán)內(nèi)沒(méi)出現(xiàn) break,也就是正常循環(huán)完成時(shí)才會(huì)執(zhí)行。首先我們來(lái)看一個(gè)插入排序法的例子:
from random import randrange
def insertion_sort(seq):
if len(seq) 1:
return seq
_sorted = seq[:1]
for i in seq[1:]:
inserted = False
for j in range(len(_sorted)):
if i _sorted[j]:
_sorted = [*_sorted[:j], i, *_sorted[j:]]
inserted = True
break
if not inserted:
_sorted.append(i)
return _sorted
print(insertion_sort([randrange(1, 100) for i in range(10)]))
[8, 12, 12, 34, 38, 68, 72, 78, 84, 90]
在這個(gè)例子中,對(duì)已排序的 _sorted 元素逐個(gè)與 i 進(jìn)行比較,若 i 比已排序的所有元素都大,則只能排在已排序列表的最后。這時(shí)我們就需要一個(gè)額外的狀態(tài)變量 inserted 來(lái)標(biāo)記完成遍歷循環(huán)還是中途被 break,在這種情況下,我們可以用 else 來(lái)取代這一狀態(tài)變量:
def insertion_sort(seq):
if len(seq) 1:
return seq
_sorted = seq[:1]
for i in seq[1:]:
for j in range(len(_sorted)):
if i _sorted[j]:
_sorted = [*_sorted[:j], i, *_sorted[j:]]
break
else:
_sorted.append(i)
return _sorted
print(insertion_sort([randrange(1, 100) for i in range(10)]))
[1, 10, 27, 32, 32, 43, 50, 55, 80, 94]
我認(rèn)為這是一個(gè)非常酷的做法!不過(guò)要注意的是,除了 break 可以觸發(fā)后面的 else 語(yǔ)句,沒(méi)有循環(huán)的時(shí)候也會(huì):
while False:
print("Will never print!")
else:
print("Loop failed!")
Loop failed!
錯(cuò)誤捕捉中的 else
try...except...else...finally 流程控制語(yǔ)法用于捕捉可能出現(xiàn)的異常并進(jìn)行相應(yīng)的處理,其中 except 用于捕捉 try 語(yǔ)句中出現(xiàn)的錯(cuò)誤;而 else 則用于處理沒(méi)有出現(xiàn)錯(cuò)誤的情況;finally 負(fù)責(zé) try 語(yǔ)句的”善后工作“ ,無(wú)論如何都會(huì)執(zhí)行??梢酝ㄟ^(guò)一個(gè)簡(jiǎn)單的例子來(lái)展示:
def divide(x, y):
try:
result = x / y
except ZeroDivisionError:
print("division by 0!")
else:
print("result = {}".format(result))
finally:
print("divide finished!")
divide(5,2)
print("*"*20)
divide(5,0)
result = 2.5 divide finished! ******************** division by 0! divide finished!
當(dāng)然,也可以用狀態(tài)變量的做法來(lái)替代 else:
def divide(x, y):
result = None
try:
result = x / y
except ZeroDivisionError:
print("division by 0!")
if result is not None:
print("result = {}".format(result))
print("divide finished!")
divide(5,2)
print("*"*20)
divide(5,0)
result = 2.5 divide finished! ******************** division by 0! divide finished!
總結(jié)
有人覺(jué)得 else 的這些用法違反直覺(jué)或者是 implicit 而非 explicit,不值得提倡。但我覺(jué)得這種”判決“需要依賴(lài)具體的應(yīng)用場(chǎng)景以及我們對(duì) Python 的理解,并非一定要對(duì)新人友好的語(yǔ)法才算是 explicit 的。當(dāng)然也不推薦在所有地方都使用這個(gè)語(yǔ)法,for/while...else 最大的缺點(diǎn)在于 else 是需要與 for/file 對(duì)齊的,如果是多層嵌套或者循環(huán)體太長(zhǎng)的情況,就非常不適合用 else(回憶一下游標(biāo)卡尺的梗就知道了:P)。只有在一些簡(jiǎn)短的循環(huán)控制語(yǔ)句中,我們通過(guò) else 擺脫一些累贅的狀態(tài)變量,這才是最 Pythonic 的應(yīng)用場(chǎng)景!
- Python深入學(xué)習(xí)之上下文管理器
- 深入解析Python中的上下文管理器
- Python中的with語(yǔ)句與上下文管理器學(xué)習(xí)總結(jié)
- 正確理解python中的關(guān)鍵字“with”與上下文管理器
- Python中的if、else、elif語(yǔ)句用法簡(jiǎn)明講解
- Python中在for循環(huán)中嵌套使用if和else語(yǔ)句的技巧
- 在Python的while循環(huán)中使用else以及循環(huán)嵌套的用法
- 在Python的循環(huán)體中使用else語(yǔ)句的方法
- Python的for和break循環(huán)結(jié)構(gòu)中使用else語(yǔ)句的技巧
- 深入學(xué)習(xí)Python中的上下文管理器與else塊
相關(guān)文章
基于Python實(shí)現(xiàn)簡(jiǎn)單的人臉識(shí)別系統(tǒng)
這篇文章主要介紹了如何通過(guò)Python實(shí)現(xiàn)一個(gè)簡(jiǎn)單的人臉識(shí)別系統(tǒng),文中的示例代碼講解詳細(xì),對(duì)我們學(xué)習(xí)Python有一定的幫助,感興趣的可以跟隨小編一起試一試2022-01-01
對(duì)Pyhon實(shí)現(xiàn)靜態(tài)變量全局變量的方法詳解
今天小編就為大家分享一篇對(duì)Pyhon實(shí)現(xiàn)靜態(tài)變量全局變量的方法詳解,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。一起跟隨小編過(guò)來(lái)看看吧2019-01-01
python實(shí)現(xiàn)自動(dòng)登錄人人網(wǎng)并訪問(wèn)最近來(lái)訪者實(shí)例
這篇文章主要介紹了python實(shí)現(xiàn)自動(dòng)登錄人人網(wǎng)并訪問(wèn)最近來(lái)訪者實(shí)例,該實(shí)例是在前面登錄人人網(wǎng)實(shí)例基礎(chǔ)上的擴(kuò)展,是非常實(shí)用的一個(gè)技巧,需要的朋友可以參考下2014-09-09
python多線程實(shí)現(xiàn)同時(shí)執(zhí)行兩個(gè)while循環(huán)的操作
這篇文章主要介紹了python多線程實(shí)現(xiàn)同時(shí)執(zhí)行兩個(gè)while循環(huán)的操作,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。一起跟隨小編過(guò)來(lái)看看吧2020-05-05
利用Python實(shí)現(xiàn)字幕掛載(把字幕文件與視頻合并)思路詳解
這篇文章主要介紹了如何利用Python實(shí)現(xiàn)字幕掛載,把字幕文件與視頻合并,本文通過(guò)實(shí)例代碼給大家介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下2020-10-10
Python簡(jiǎn)單的制作圖片驗(yàn)證碼實(shí)例
本篇文章主要介紹了Python簡(jiǎn)單的制作圖片驗(yàn)證碼實(shí)例,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2017-05-05
python機(jī)器學(xué)習(xí)pytorch自定義數(shù)據(jù)加載器
這篇文章主要為大家介紹了python機(jī)器學(xué)習(xí)pytorch自定義數(shù)據(jù)加載器使用示例學(xué)習(xí),有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2022-10-10
Python在字典中獲取帶權(quán)重的隨機(jī)值實(shí)現(xiàn)方式
這篇文章主要介紹了Python在字典中獲取帶權(quán)重的隨機(jī)值,本文通過(guò)實(shí)例代碼給大家介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下2022-11-11

