小烏龜趴趴走 -- 007
在前面的一篇短文中﹐我們學會了使用對話小視窗﹐讓使用的人決定要以多長的半徑
來畫圓圈圈。美中不足的是﹐您每 run 一次這個電腦程式﹐只能決定一次圓圈的半
徑。在文章的末尾﹐我自問自答說﹐有沒有可能在 run 一次這個電腦程式時﹐使用
者得以決定使用不同的半徑﹐畫許許多多﹐大大小小的圓圈圈﹐直到盡興了﹐不想
畫了為止?我的答案是﹐可能。
要如何才能辦到呢?我們必須回到在「小烏龜趴趴走 -- 005」中所介紹的 looping
這個話題。在那兒﹐我們提到﹐如果要重複做一件事﹐我們可以使用 loop 這個結
構。我想您還記得﹐基本而言﹐有兩種形態的 loop。一種是事先就知道需要重複幾
次的 loop (例如我們知道畫五角形需要重複五次)﹐那種 loop 通常就叫 for loop
(因為指令是以 for 這個字開始)。第二種情形就是事先並不知道要重複多少次的
loop (例如我們不知道一個人要畫多少個圓圈圈才會盡興而不再畫) ﹐這種形態
的 loop 通常就叫做 while loop (因為指令是以 while 這個字開始)。這個指令
的結構是﹐在 while 這個 key word 後面﹐跟着一個 condition。如果這個
condition 經過檢測的結果是 True (真實)的話﹐就執行屬於 loop 裡頭的指令﹐
否則就跳離這個 loop。它的語言架構如下所示:
while condition:
statement-1
statement-2
.
.
現在回過頭來考慮畫圓圈這個問題。我們怎麼知道使用者想畫或是不想畫了呢?除
了問使用者之外﹐我們是無法預先知道使用者的心意的。要怎麼問呢?我們當然也
可以使用對話小視窗﹐在每畫完一個圓之後﹐就問使用者是否還要再畫?如果使用
者說「不」﹐我們就可以跳離那個 while loop 了。不過﹐這兒所要使用的對話小
視窗與前一篇文章所介紹的有些不同﹐因為這回使用者在鍵盤上輸入的不是一個數
字﹐而是文字「是」或「否」。因此﹐我們所要用的指令是︰
textinput("標題"﹐ "要對使用者說的話")
例如:
textinput("Draw another circle?"﹐ "Want to draw another circle? (y/n)")
綜合上面的討論﹐我們的程式會有類似下面的結構:
1. 進入 while loop (將 condition 設定為 True):
2. 請使用者輸入要畫的圓的半徑
3. 根據上個步驟所獲得的半徑畫出一個圓形
4. 問使用者是否要再畫一個圓?
5. 如果使用者的回答等於「是」的話﹐就回到第一個步驟﹐重新進入這個 while
loop﹐否則就跳離這個 while loop。
將上面的結構轉換成「大蟒蛇」的指令﹐我們就寫成了下面的程式:
from turtle import *
shape("turtle")
color("red", "yellow")
while True:
radius = numinput("Radius", "Please enter the radius of a circle")
circle(radius)
answer = textinput("Draw another circle?", "Want to draw another circle? (y/n)")
if answer == "y":
pass
else:
break
done()
上圖顯示在畫完一個圓圈後﹐對話小視窗出現了﹐問是否要再畫圓圈?我輸入了一個
y﹐滑鼠正指向 OK 這個 button。
在上面的程式中﹐我們新介紹了一個 if statement。在我們的例子中﹐基本上是說:
假如使用者的回答(answer)是等於 y 的話﹐就 pass 回到 while loop 的入口
(也就是回到 while True: 那個指令)﹐否則的話﹐就跳出這個 loop (那就是
break 的意思)。在上面的例子中﹐ while﹐True﹐if﹐pass 還有 break 等等﹐
都是「大蟒蛇」的 key words﹐有其特定的意義﹐它們是大寫或是小寫﹐也必須完
全如上面所示﹐不能更改。
另外要一提的是﹐在上面我們問使用者是否要再畫另一個圓﹐如果使用者想再畫一
個圓﹐就必須在鍵盤上輸入一個小寫的 y﹐要是輸入大寫的 Y 或是 YES﹐甚至 Yes﹐
yes 等等﹐都會被認為不等於 y﹐換句話說﹐就會被認為「不想再畫了」﹐這顯然
是限制太嚴﹐太沒有彈性了。這個問題當然是可以解決的。只是若要充份說明的話﹐
就涉及許多其他的觀念和指令的運用﹐所以在此我就暫時不多說了。
還有﹐您需要了解 = 和 == 的區別。我們提了好幾次﹐等號(=)把 assignment
statement 分隔成兩部份﹐在等號右邊的 expression 先被評估計算所獲得的結果﹐
會被儲存在等號左邊所指定的電腦記憶體的某個地方。而 == 則是等於的意思﹐例
如 if answer == "y" 的意思就是說﹐如果 answer 等於 "y" 這件事屬實的話﹐就
……
所以千萬不要把 = 以及 == 的意義搞混了。老一點的電腦語言幾乎都是用同一個
= 這個符號用來代表 assignment 和等於這兩種截然不同的意義﹐以致造成許多迷
惑與混亂﹐所以新的電腦語言多半使用 = 以及 == 來區分它們不同的用意。
上面的程式﹐讓使用者在開始 run 電腦程式後﹐可以畫許許多多﹐大大小小的圓形﹐
直到不想再畫為止。不過﹐這個程式有一個問題﹐那就是每個畫上去的圓圈圈都留
在螢幕上﹐在畫了許多圓圈圈之後﹐就會讓人覺得眼花繚亂了。有沒有可能在畫下
一個圓圈圈之前﹐先把上一次所畫的圓圈圈擦拭乾淨呢?答案是﹐可以呀﹐您只需
加上一個 clear() 這個指令就行了。
下面就是經過修改的程式。
from turtle import *
shape("turtle")
color("red", "yellow")
while True:
radius = numinput("Radius", "Please enter the radius of a circle")
circle(radius)
answer = textinput("Draw another circle?", "Want to draw another circle? (y/n)")
if answer == "y":
clear()
else:
break
done()
(2011-10-19)
【附記】
現在您也可以試著修改您畫多角形(多邊形)的程式﹐使它畫不同大小﹐不同形狀的
多邊形﹐直到使用者不想再畫了為止了。
微光中的歌吟