C 語言初學教材 - 第三章 無窮迴圈的陷阱

迴圈也有可能會是無窮無盡的執行下去,像是我們常用的任何 GUI 介面的軟體,基本上,一個視窗要持續顯示在螢幕上,就需要靠一個不會輕易結束的迴圈,有時候就像是無窮迴圈一樣。



只不過,無窮迴圈是真的不會結束,因此會造成程式當掉或系統崩潰的麻煩。因此,幾乎我們常用的任何 GUI 軟體都有設計結束的機制,不然的話,就得呼叫作業系統來強制關閉囉!作業系統也關閉不了的話,就會有當機的風險。


for 迴圈雖然有明確重複的控制機制,但也可以規劃成像是無窮迴圈的執行模式,例如,所需要的三個運算式之中,只有結束條件是必須的,這是說其他兩個可以留空白,如下
for (;1;) {
    printf("0");
}


如果程式中加入了上面三行程式碼,這個程式執行到這裡就會一直在印幕上印 0 ,一直印下去不會結束。


接下來,我們繼續把猜數字遊戲的 for 迴圈改成無窮迴圈,結束的機制很簡單,猜對了就會用 break 陳述跳出迴圈
#include <stdio.h>
#include <time.h>
#include <math.h>

enum STATE {RIGHT = 1, BIG_FOUR ,BIG_FIVE, SMALL_FOUR, SMALL_FIVE};

int main(void)
{
    int answer = time(NULL);
    int guess;
    int diff;
    int state = 0;
    int counter = 0;
    
    answer %= 25;
    if (answer == 0) {
        answer = 25;
    }
    
    for (;1;) {
        printf("請猜一個數字 1 到 25: ");
        scanf("%d", &guess);
        diff = guess - answer;
        diff = (int) fabs(diff);
    
    
        if (guess == answer) {
            state = RIGHT;
        }
        else {
            counter++;
            
            if (guess > answer) {
                if (diff > 5) {
                    state = BIG_FIVE;
                }
                else {
                    state = BIG_FOUR;
                }
            }
            else {
                if (diff > 5) {
                    state = SMALL_FIVE;
                }
                else {
                    state = SMALL_FOUR;
                }
            }
        }
    
        if (state == RIGHT) {
            printf("猜對囉!\n");
            break;
        }
        else if (state == BIG_FIVE) {
            printf("猜的數字比答案大....還很遠,再加把勁!\n");
        }
        else if (state == BIG_FOUR) {
            printf("猜的數字比答案大....不錯喔!很接近了\n");
        }
        else if (state == SMALL_FIVE) {
            printf("猜的數字比答案小....還很遠,再加把勁!\n");
        }
        else if (state == SMALL_FOUR) {
            printf("猜的數字比答案小....不錯喔!很接近了\n");
        }
        else {
            printf("猜錯囉!\n");
         }
    }
    
    if (counter == 0) {
        printf("\n\n很棒喔!一次就猜對!\n");
    }
    else if (counter > 5) {
        printf("\n\n總算有猜對,一共猜了 %d 次,下次加油喔!\n", counter + 1);
    }
    else {
        printf("\n\n猜了 %d 次,不錯不錯!\n", counter + 1);
    }
    
    return 0;
}

/* 《程式語言教學誌》的範例程式
    http://pydoing.blogspot.com/
    檔名:gn8.c
    功能:簡單的猜數字遊戲
    作者:張凱慶
    時間:西元2010年7月 */ 


我們刪除原先 counter == 10 的那一段,然後將 counter > 5 所要顯示的訊息更改如下
printf("\n\n總算有猜對,一共猜了 %d 次,下次加油喔!\n", counter + 1);


這樣結束都會顯示猜測的次數。


好了,來編譯玩玩看吧!不必怕猜了十次猜不到就被遊戲程式虧了說。



問題與討論
  1. 為什麼說無窮迴圈是陷阱?
  2. 什麼情況需要用到無窮迴圈?
  3. 說明這個猜數字遊戲的結束機制。




沒有留言: