main() 函式的返回值

由於函式值的原定資料型態就是整數,所以它可以不寫。 例如將以下宣告

int ipow(int, int);
改成這個宣告也是一樣的:
ipow(int, int);
(有些編譯程式會給 warning 訊息,不過不要緊。)

讓我們再回頭看看 main() 函式。 通常我們沒有寫它的函式值。現在知道,它並非沒有函式值, 而是心照不宣地假設了 int 函式值。 我們不曾在 main() 之內寫過 return 語句, 這樣做並不正確,只是 C 語言並沒有嚴格地要求函式值: 即使宣告了函式值,只要原函式沒有要求那個函式值, 那麼,沒有寫 return 就沒有關係。

讀者可能已經在心中產生了一個問題:

不是說 main() 函式是一套程式的主函式嗎?它已經是最上層的函式,哪裡來的原函式?
這就要牽涉到作業系統了。我們以 UNIX 為例來說明。 以整個 UNIX 的眼光來看, 您寫的 main() 是被一個使用者介面程式呼叫的。 例如,一個 C 程式編譯後的檔案名叫做 a.out, 您是如何執行 a.out 的呢? 您是在一個介面程式中下指令 a.out 來執行它。 所以,其實是您的介面程式呼叫了 main() 函式。 介面程式,就是 main() 的原函式。

如果我們在 main() 裡面寫了 return 語句, 還了一個整數給原函式,也就是還給了介面程式。 那個值到哪裡去了呢? 這要看介面程式的設計而定。 以 C shell 或 T-C shell 為例, 函式值,如果有的話,就成為 status 介面參數的值。

main() 傳回它的函式值給介面程式, 這個傳回的值又稱為 返回值 (return value)。

所有 UNIX 的標準指令,都是用 C 語言寫的,而且也都會還一個返回值。 您可以試試看

ls
然後立刻說
echo $status
看看 status 的參數值。應該是 0。 同理,可以試試看 catcp 這些指令, 只要執行成功了,status 都是 0。 但是,如果執行不成功,就會出現正數的 status。 您可以試試看 (要以普通使用者的身分試)
rm /etc
應該會看到錯誤訊息,不能刪除這個資料夾。接著立刻說
echo $status
應該是 1 或 2。

注意,因為每個 UNIX 指令在執行後都可能會有一個返回值, 所以,執行後要立刻檢查這個值。 否則,只要執行了下一個指令,status 參數就變成新指令的返回值了。

這是 UNIX 系統的設計規範。如果一個程式執行成功,正常地結束了, 它的返回值就應該是 0。 如果它在執行中遇到錯誤,其返回值就應該是一個正整數。 在技術手冊中,應該說明不同的正返回值所代表的不同意義。 這些返回值,在介面腳本程式 (shell scripts) 中扮演重要的角色。 這是學習 UNIX 作業系統的課題, 就不在此深入介紹了。

現在,請重新編譯這個 hello world 程式, 執行後檢視它的返回值。


#include <stdio.h>

/* 第一個 C 程式,有函式值  (main-return.c) */
main() {
    printf("hello, world\n");
    return 0;
}

我們通常也不會在 main()( ) 內寫參數。 現在知道,這並不表示 main() 沒有參數, 如果沒有的話,應該寫 void 才對。 其實 main() 是有參數的,只是我們目前還沒有用到它們而已。 換句話說,main() 的原函式有傳來參數, 只是我們到目前為止所寫的 main() 函式, 都沒有接收那些參數。 這個技術,留到稍後再說明。

習題

  1. 嘗試發現 UNIX 的 ls 指令, 什麼時候會返回非零的值?

[ 前一節 ]‧[ 後一節 ]‧[ 回目錄 ]



注意:此處所有文件均為原著,個別的版權宣告日後會一一公布, 整體版面設計亦尚未完成。但仍請勿抄襲文字與圖片,以免觸犯著作權法。

Created: Apr 2, 2000
Last Revised: Apr 2, 2000
© Copyright 2000 Wei-Chang Shann 單維彰

shann@math.ncu.edu.tw