首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> 更多程式語言 >> 程式設計綜合問答

C 語言指標參數傳遞陷阱:為何函數內 malloc 不影響外部指標

     編輯:程式設計綜合問答

C 語言只有值傳遞。函數參數 int *p 接收的是呼叫端指標變數的位址值副本。函數內 p = malloc(...) 修改的是區域副本,呼叫端原指標仍指向原位址(通常為 NULL/隨機值),導致後續解參考崩潰。

錯誤代碼

void alloc(int *p) {
    p = malloc(sizeof(int)); // 修改區域副本
    *p = 10;
}
int main() {
    int *ptr = NULL;
    alloc(ptr);
    printf("%d", *ptr); // Segmentation fault:ptr 仍為 NULL
}

正確做法:傳遞指標的指標(二級指標)

void alloc(int **p) { // 接收指標的位址
    *p = malloc(sizeof(int)); // 解參考修改原指標指向
    **p = 10;
}
int main() {
    int *ptr = NULL;
    alloc(&ptr); // 傳遞 ptr 的位址
    printf("%d", *ptr); // 10
    free(ptr);
}

符號辨析

記憶體圖解

main 棧框:          alloc 棧框:
ptr (0x7fff...) --> NULL      p (0x7ffe...) --> NULL (副本)
                            p = malloc() --> 0x5555... (新堆積)
                            *p = 10
返回後: ptr 仍指向 NULL,0x5555... 成為記憶體洩漏

進階:C++ 參考傳遞簡化語法

void alloc(int *&p) { // 參考傳遞,p 成為原指標別名
    p = new int(10);
}
int main() {
    int *ptr = nullptr;
    alloc(ptr); // 直接傳 ptr,無需 &ptr
    cout << *ptr; // 10
}

核心口訣

「要在函數內修改呼叫端的指標指向,必須傳遞指標的位址(二級指標)或用 C++ 參考。」

這是 C 語言指標教學中最經典、最易錯、最必須掌握的概念。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved
運算式意義型別
*p解參考:存取 p 指向的記憶體int (若 p 為 int*)
&p取址:獲得指標變數本身的位址int** (若 p 為 int*)
*&p先取址再解參考,等價於 p 本身int*