C 語言函式 (Functions)

隨著程式越來越複雜,如果把所有程式碼都寫在 main 裡面,會變得很難閱讀和維護。函式 (Function) 允許我們將特定的功能獨立出來,變成一個個小模組。

其實我們已經用過函式了:printf 是 C 語言提供的函式,而 main 是我們自己寫的函式。

函式的組成

一個函式通常包含三個部分:

  1. 宣告 (Declaration) / 原型 (Prototype):告訴編譯器這個函式長什麼樣子(名稱、參數、回傳型態),通常寫在 main 之前或標頭檔中。
  2. 定義 (Definition):函式實際執行的內容。
  3. 呼叫 (Call):使用這個函式。
#include <stdio.h>

// 1. 函式宣告
int add(int a, int b);

int main() {
    int sum;
    
    // 3. 呼叫函式
    sum = add(10, 20);
    printf("10 + 20 = %d\n", sum);
    
    return 0;
}

// 2. 函式定義
// 回傳型態 函式名稱(參數列)
int add(int a, int b) {
    int result = a + b;
    return result; // 回傳計算結果
}

參數傳遞 (Parameters)

  • 參數 (Parameter):函式定义時括號內的變數(如上例的 a, b)。
  • 引數 (Argument):呼叫函式時實際傳入的值(如上例的 10, 20)。

傳值呼叫 (Call by Value)

在 C 語言中,預設是將數值複製一份給函式。所以在函式內修改參數的值,不會影響到原本的變數。

void changeNum(int x) {
    x = 100; // 這裡改的是 x 的副本
}

int main() {
    int num = 10;
    changeNum(num);
    printf("%d", num); // 輸出還是 10
}

如果要修改原本的變數,需要用到之後會教的指標(傳址呼叫)。

變數作用域 (Scope)

  • 區域變數 (Local Variable):在函式內宣告的變數。只在該函式內有效,函式執行完就消失。
  • 全域變數 (Global Variable):在所有函式外面宣告的變數。整個程式都能存取。
int globalVar = 100; // 全域變數

void func() {
    int localVar = 50; // 區域變數
    // 這裡可以存取 globalVar
}

int main() {
    // 這裡不能存取 localVar
    return 0;
}

遞迴 (Recursion)

函式可以呼叫自己,這叫做遞迴。經典例子是計算階乘。

int factorial(int n) {
    if (n == 0) // 終止條件 (Base Case)
        return 1;
    else
        return n * factorial(n - 1);
}

使用遞迴時務必注意終止條件,否則會造成堆疊溢位 (Stack Overflow)。