<kbd id="afajh"><form id="afajh"></form></kbd>
<strong id="afajh"><dl id="afajh"></dl></strong>
    <del id="afajh"><form id="afajh"></form></del>
        1. <th id="afajh"><progress id="afajh"></progress></th>
          <b id="afajh"><abbr id="afajh"></abbr></b>
          <th id="afajh"><progress id="afajh"></progress></th>

          Python 為什么不設(shè)計(jì) do-while 循環(huán)結(jié)構(gòu)?

          共 522字,需瀏覽 2分鐘

           ·

          2022-01-20 13:40

          △點(diǎn)擊上方“Python貓”關(guān)注 ,回復(fù)“1”領(lǐng)取電子書(shū)

          作者:豌豆花下貓
          來(lái)源:Python貓

          在某些編程語(yǔ)言中,例如 C/C++、C#、PHP、Java、JavaScript 等等,do-while 是一種基本的循環(huán)結(jié)構(gòu)。

          它的核心語(yǔ)義是:先執(zhí)行一遍循環(huán)體代碼,然后執(zhí)行一遍條件語(yǔ)句,若條件語(yǔ)句判斷為真,則繼續(xù)執(zhí)行循環(huán)體代碼,并再次執(zhí)行條件語(yǔ)句;直到條件語(yǔ)句判斷為假,則跳出循環(huán)結(jié)構(gòu)。

          流程圖如下(Java 示例):

          //?打印小于?20?的數(shù)字
          public?class?Test?{
          ???public?static?void?main(String[]?args){
          ??????int?x?=?10;
          ??????do?{
          ?????????System.out.print("value?of?x?:?"?+?x?);
          ?????????x++;
          ?????????System.out.print("\n");
          ??????}?while(x?20);
          ???}
          }

          Python 并不支持 do-while 結(jié)構(gòu),“do”并不是一個(gè)有效的關(guān)鍵字。

          那么,為什么 Python 不提供這種語(yǔ)法結(jié)構(gòu)呢,這種現(xiàn)狀的背后有何種設(shè)計(jì)考量因素呢?

          在回答這個(gè)問(wèn)題之前,讓我們?cè)僮屑?xì)思考一下 do-while 語(yǔ)法可以解決什么問(wèn)題,看看使用這種結(jié)構(gòu)能帶來(lái)什么好處?

          最顯而易見(jiàn)的好處是:do-while 語(yǔ)法保證了會(huì)先執(zhí)行一遍循環(huán)體代碼。

          它的使用場(chǎng)景也許不多,但是,跟普通的 while 循環(huán)或者 for 循環(huán)語(yǔ)法的“條件前置”思想不同,它體現(xiàn)的是一種“條件后置”的編程邏輯,也是一種控制循環(huán)的常見(jiàn)方式。

          它們的關(guān)系似乎有點(diǎn)像 C/C++ 這些語(yǔ)言中的i++++i操作的區(qū)別,在某些特殊場(chǎng)合中,也許會(huì)更為高效。

          除了這一特點(diǎn),這種結(jié)構(gòu)最大的應(yīng)用場(chǎng)景其實(shí)是在 C/C++ 中特殊的do {...} while (0) 用法。這在很多開(kāi)源項(xiàng)目的源碼中都能找到蹤跡,例如 Linux、Redis 以及 CPython 解釋器,等等。

          這里面的數(shù)字 0 表示布爾值 False,意味著循環(huán)只會(huì)執(zhí)行一遍,然后就跳出。

          這樣的寫法是不是很詭異?所謂“循環(huán)”,一般就意味著程序體會(huì)被反復(fù)執(zhí)行多次,但是,do {...} while (0) 卻偏偏只需要它執(zhí)行一遍,這初看起來(lái)是有點(diǎn)多余啊。

          這種寫法主要用在宏函數(shù)的定義中,可以解決宏代碼塊的編譯問(wèn)題,使代碼按照我們的意圖而合理分塊。

          另外,do {...} while (0) 結(jié)合 break 使用,還可以實(shí)現(xiàn)很優(yōu)雅的跳轉(zhuǎn)控制效果。

          在下面的示例中,步驟 1、4 和 5 要求必須執(zhí)行,而步驟 2 取決于步驟 1 的執(zhí)行結(jié)果,步驟 3 則取決于步驟 2 的執(zhí)行結(jié)果。

          do?{
          ??//?執(zhí)行步驟?1?
          ??if?(條件1失敗)?{
          ????break;
          ??}
          ??//?執(zhí)行步驟?2?
          ??if?(條件2失敗)?{
          ????break;
          ??}
          ??//?執(zhí)行步驟?3?
          ??if?(條件3失敗)?{
          ????break;
          ??}
          }?while(0);
          //?執(zhí)行步驟?4
          //?執(zhí)行步驟?5

          在這種場(chǎng)景中,我們確實(shí)只需要按照順序執(zhí)行一遍。do-while 結(jié)構(gòu)很清晰,避免造成多層條件嵌套或者設(shè)置諸多額外標(biāo)記的局面。

          最后還有一點(diǎn),在匯編層面,do-while 比 while 更接近匯編語(yǔ)言的邏輯,可以節(jié)省使用指令,在過(guò)去的低內(nèi)存時(shí)代,算得上是一種優(yōu)化寫法。

          分析完 do-while 的好處后,讓我們回到主題:Python 為什么不需要設(shè)計(jì) do-while 循環(huán)語(yǔ)法呢?

          首先,Python 離底層應(yīng)用編程太遠(yuǎn)了,就不用考慮匯編指令的優(yōu)化了,同時(shí),它也不涉及宏的使用。

          至于“條件前置”和“條件后置”的區(qū)別,其實(shí)并沒(méi)有太大影響,而且,由于 Python 使用簡(jiǎn)潔優(yōu)雅的縮進(jìn)加冒號(hào)語(yǔ)法來(lái)劃分代碼塊,導(dǎo)致直譯過(guò)來(lái)的 do-while 語(yǔ)法看起來(lái)會(huì)很怪異(注意,直譯的 while 的條件后沒(méi)有其它內(nèi)容):

          do:
          ????pass
          while?False

          想要引入新的語(yǔ)法特性,必然要遵守既定的風(fēng)格習(xí)慣。其它語(yǔ)言的 do-while 結(jié)構(gòu)直譯成 Python 的話,肯定不合適。

          事實(shí)上,在 2003 年時(shí),有一個(gè) PEP 提議給 Python 加上 do-while 語(yǔ)法支持:

          PEP-315 Enhanced While Loop

          該 PEP 提議增加一個(gè)可選的 do 子句,支持將 while 循環(huán)擴(kuò)展成這樣子:

          do:
          ????
          while?:
          ????

          這不是簡(jiǎn)單地從其它語(yǔ)言翻譯成 Python,它的 while 語(yǔ)句后保留了 Python 的縮進(jìn)用法,并不會(huì)造成直譯形式的突兀結(jié)果。

          加上 while 循環(huán)本身已支持的可選的 else 子句,因此,while 完整的語(yǔ)法結(jié)構(gòu)是這樣的:

          while_stmt?:?["do"?":"?suite]
          ????????????"while"?expression?":"?suite
          ????????????["else"?":"?suite]

          (PS.在本系列的下一篇文章,我們將解釋為什么 Python 要支持 while-else 語(yǔ)法)

          也就是說(shuō),在保持原 while 循環(huán)語(yǔ)法不變的情況下,PEP-315 提議支持在 while 前面使用一個(gè)可選的 do 子句。

          do 子句只會(huì)執(zhí)行一遍,當(dāng)它里面出現(xiàn) break 時(shí),則跳出整個(gè) do-while 循環(huán);當(dāng) do 子句中出現(xiàn) continue 時(shí),則跳出 do 子句,進(jìn)到 while 的條件判斷中。

          有了 do 子句后,很容易就能實(shí)現(xiàn) do {...} while (0) 的跳轉(zhuǎn)控制效果。

          但是,這個(gè) PEP 遭到了一些核心開(kāi)發(fā)者的反對(duì)。

          反對(duì)的理由是,不需要引入新的關(guān)鍵字和語(yǔ)法,僅使用現(xiàn)有語(yǔ)法就能很好地實(shí)現(xiàn)同樣的功能:

          while?True:
          ????
          ????if?not?:
          ????????break
          ????

          Python 之父 Guido van Rossum 也持反對(duì)意見(jiàn),他的原話是:

          Guido的回復(fù)

          Please reject the PEP. More variations along these lines won't make the language more elegant or easier to learn. They'd just save a few hasty folks some typing while making others who have to read/maintain their code wonder what it means.

          簡(jiǎn)單翻譯一下,這種 do-while 語(yǔ)法并不會(huì)使 Python 更優(yōu)雅好用,反而會(huì)產(chǎn)生閱讀/維護(hù)代碼的理解負(fù)擔(dān)。

          就個(gè)人的感覺(jué)而言,我也不贊成引入 PEP-315 那種可選的 do-while 語(yǔ)法,雖然它比固定形式的 do-while 結(jié)構(gòu)更為靈活和優(yōu)雅一點(diǎn)。

          最后稍微總結(jié)一下,do-while 作為一種常見(jiàn)的循環(huán)結(jié)構(gòu),在其它語(yǔ)言中有所發(fā)揮,它甚至還發(fā)展出了do {...} while (0) 的典型用法,但是,do-while 能夠解決的幾個(gè)問(wèn)題要么在 Python 中并不存在(宏定義、匯編指令),要么就是已經(jīng)有更為合適而低成本的實(shí)現(xiàn)(跳轉(zhuǎn)控制)。

          看完這篇文章,你是否還有其它補(bǔ)充的內(nèi)容呢?歡迎交流討論。

          如果你對(duì) Python 語(yǔ)言設(shè)計(jì)相關(guān)的話題感興趣,歡迎訂閱 Github 上的《Python為什么》系列文章(https://github.com/chinesehuazhou/python-whydo

          關(guān)聯(lián)閱讀:

          Python 為什么會(huì)有個(gè)奇怪的“...”對(duì)象?

          Python 函數(shù)為什么會(huì)默認(rèn)返回 None?

          Python 之父為什么嫌棄 lambda 匿名函數(shù)?

          為什么繼承 Python 內(nèi)置類型會(huì)出問(wèn)題?!

          Python 為什么推薦蛇形命名法?

          如果你覺(jué)得本文有幫助
          請(qǐng)慷慨分享點(diǎn)贊,感謝啦
          瀏覽 65
          點(diǎn)贊
          評(píng)論
          收藏
          分享

          手機(jī)掃一掃分享

          分享
          舉報(bào)
          評(píng)論
          圖片
          表情
          推薦
          點(diǎn)贊
          評(píng)論
          收藏
          分享

          手機(jī)掃一掃分享

          分享
          舉報(bào)
          <kbd id="afajh"><form id="afajh"></form></kbd>
          <strong id="afajh"><dl id="afajh"></dl></strong>
            <del id="afajh"><form id="afajh"></form></del>
                1. <th id="afajh"><progress id="afajh"></progress></th>
                  <b id="afajh"><abbr id="afajh"></abbr></b>
                  <th id="afajh"><progress id="afajh"></progress></th>
                  性爱久久| 亚洲综合精品久久婷婷无码专区 | www.色天堂 | 做爱小视频网站 | 日韩黄色视频 |