出場(chǎng)人物介紹:
小美:小學(xué)4年級(jí)學(xué)生,參加了學(xué)校的編程興趣小組,已經(jīng)了解了Python語(yǔ)言的基本語(yǔ)法进苍,能夠看懂一些簡(jiǎn)單的程序。她做事風(fēng)風(fēng)火火鸭叙,對(duì)所有的事情都很好奇觉啊,喜歡打破砂鍋問(wèn)到底,是一個(gè)叫人又愛(ài)又恨的小丫頭沈贝。
阿福:一個(gè)酷愛(ài)編程的8年級(jí)男生杠人。大家都說(shuō)他長(zhǎng)得像國(guó)寶大熊貓,動(dòng)作緩慢,憨態(tài)可掬嗡善。他做事情確實(shí)夠慢的辑莫,連說(shuō)話也慢條斯理,可是他一點(diǎn)也不擔(dān)心罩引,他常常說(shuō):“慢就是快各吨,只要堅(jiān)持下去,蝸牛也能爬上金字塔袁铐〗已眩”
古老師:雖然年近不惑,但依然對(duì)生活充滿熱情剔桨√敫“愛(ài)生活?lèi)?ài)運(yùn)動(dòng)”是他的人生信條,和孩子們一起編程是他最大的樂(lè)趣领炫。他神出鬼沒(méi)偶垮,總是在孩子們最需要幫助的時(shí)候出現(xiàn)。當(dāng)然帝洪,你也不能動(dòng)不動(dòng)就找古老師似舵,因?yàn)樗苊Γ浅7浅CΥ邢俊K匝饣龅絾?wèn)題還是自己先思考吧。
正文
列表的紛爭(zhēng)之雙指針掃描
小美:最近我們學(xué)習(xí)了一種新的數(shù)據(jù)結(jié)構(gòu)——列表砰奕。列表比字符串靈活多了蛛芥,它不僅可以修改元素值,還可以隨意增加和刪除元素军援,功能十分強(qiáng)大仅淑。
阿福:是啊,列表是Python語(yǔ)言中使用非常廣泛的一種數(shù)據(jù)結(jié)構(gòu)胸哥,它的內(nèi)置函數(shù)很豐富涯竟,功能十分強(qiáng)大。
小美:列表的內(nèi)置函數(shù)確實(shí)太“豐富”了空厌,我怎么也記不住庐船。對(duì)了,阿福你是怎么記住這些函數(shù)的呢嘲更?
阿福:我也沒(méi)什么好的方法筐钟,就是多記多用唄。
古老師:沒(méi)錯(cuò)赋朦,學(xué)習(xí)不能老想著走捷徑篓冲!成功的秘訣就是熟能生巧李破。不過(guò)要想深刻地理解Python的內(nèi)置函數(shù),除了多運(yùn)用它們解決實(shí)際問(wèn)題以外纹因,嘗試自定義函數(shù)來(lái)實(shí)現(xiàn)相同的功能也是一種很好的方法喷屋。
小美:自定義函數(shù)?
阿福:用戶自己創(chuàng)造的用來(lái)實(shí)現(xiàn)某種特定功能的函數(shù)就叫自定義函數(shù)瞭恰。
古老師:阿福說(shuō)的沒(méi)錯(cuò)屯曹。那我今天就來(lái)考考你們,能否編寫(xiě)一個(gè)自定義函數(shù)來(lái)實(shí)現(xiàn)列表中reverse()方法的功能惊畏。
知識(shí)小貼士:
Python3 List? reverse()方法:reverse() 函數(shù)用于反向列表中元素恶耽。它的語(yǔ)法是list.reverse(),該方法沒(méi)有形式參數(shù)颜启,也沒(méi)有返回值偷俭,但是會(huì)對(duì)列表的元素進(jìn)行反向排序。
小美:這有什么難的缰盏,看我的涌萤!
問(wèn)題1:
反向列表中元素
函數(shù)功能:將輸入的列表的元素進(jìn)行反向排序
函數(shù)名:my_reverse(a:list) -> None
參數(shù)表:a -- 列表。
返回值:該函數(shù)沒(méi)有返回值口猜,但是會(huì)對(duì)列表a的元素進(jìn)行反向排序负溪。
示例:輸入a=[1,6,5,2],函數(shù)運(yùn)行后a=[2,5,6,1]
代碼1:
defmy_reverse(a: list) -> None:
??? n = len(a)
??? for i in range(n//2):
??????? a[i], a[n-i-1] = a[n-i-1], a[i]
阿福:我也寫(xiě)好了济炎。
代碼2:
defmy_reverse2(a: list) -> None:
??? L, R = 0, len(a) - 1
??? while L < R:
??????? a[L], a[R] = a[R], a[L]
????? ??L, R = L + 1, R – 1
古老師:都很棒川抡!小美使用單指針掃描技術(shù),分別用a[i]和a[n-i-1]來(lái)表示兩個(gè)對(duì)稱(chēng)的元素须尚,讓它們進(jìn)行交換操作崖堤,這樣只需使用一個(gè)循環(huán)變量掃描半個(gè)列表,代碼簡(jiǎn)潔耐床,效率也很高密幔。但我更推崇阿福的做法,他使用了所謂的雙指針掃描技術(shù)撩轰,分別用L和R兩個(gè)變量從兩邊向中間掃描老玛,直接交換a[L]和a[R],直到L和R相遇钧敞。這種做法思路非常清晰,代碼的含義也很明確麸粮,是可讀性很強(qiáng)的代碼溉苛。
阿福:謝謝老師夸獎(jiǎng)!呵呵弄诲。
小美:看你美的愚战!不就是雙指針嗎娇唯?功能還不是和我的單指針一樣?說(shuō)不定效率還沒(méi)有我的高呢寂玲!
古老師:小美你還別不服氣塔插,雙指針掃描確實(shí)是一種既好看又實(shí)用的方法,很多時(shí)候它能完成單指針?biāo)霾坏降氖虑橥赜础1热缦旅孢@個(gè)例子:
問(wèn)題2:
奇偶數(shù)分組
函數(shù)功能:將輸入的列表元素按照奇偶性分組想许,其中奇數(shù)劃到左側(cè),偶數(shù)劃到右側(cè)
函數(shù)名:group(a: list)-> None
參數(shù)表:a -- 列表断序。
返回值:該函數(shù)沒(méi)有返回值流纹,但是會(huì)對(duì)列表a的元素按照奇偶性分組。
示例:輸入a=[1,6,5,2]违诗,函數(shù)運(yùn)行后a=[1,5,6,2]
小美:奇偶數(shù)分組漱凝?要用到雙指針掃描?該怎么做呢诸迟?
古老師:又到了說(shuō)再見(jiàn)的時(shí)候了茸炒。你們先自己想想看吧,實(shí)在做不出再來(lái)找我阵苇,先走了壁公,拜拜。
彩蛋:
小美:古老師每次都賣(mài)關(guān)子慎玖。阿福贮尖,你想到辦法了嗎?
阿福:有點(diǎn)思路了趁怔,好像跟反轉(zhuǎn)列表的方法差不多湿硝,但這里需要用到二重循環(huán),否則不好表達(dá)润努。小美关斜,你知道二重循環(huán)嗎?
小美:知道啊铺浇,不就是循環(huán)里面套循環(huán)嘛痢畜。
阿福:知道就好,我還怕你看不懂我寫(xiě)的程序呢鳍侣。你看:
代碼3:
def group(a:list) -> None:
??? L, R = 0, len(a) - 1
??? while L < R:
??????? while a[L] % 2 == 1: #跳過(guò)左側(cè)的奇數(shù)
??????????? L += 1
??????? while a[R] % 2 == 0: #跳過(guò)右側(cè)的偶數(shù)
??????????? R -= 1
??????? if L < R:
??????????? a[L], a[R] = a[R], a[L]#將元素交換到正確的一側(cè)
??????????? L, R = L + 1, R - 1 #交換好后各自前行一步丁稀,效率更高