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

C 語言動態內存傳參陷阱:為何函數內修改指針指向外部不生效?

     編輯:程式設計綜合問答

錯誤代碼

char *p = NULL;
p = malloc(strlen(a[0]) + 1);
strcnp(a[0], p); // 函數內 p = 新地址
printf("%s", p); // 仍指向舊 malloc 內存(未被複製內容)

函數實現

char *strcnp(char *sd, char *ds) {
    char *q = sd;
    while ((*ds++ = *sd++) != '\0') ;
    return q; // 返回源地址,未修改 ds 指向
}

根因

C 語言參數按值傳遞。ds 是 p 的副本,函數內 ds = new_addr 只改變副本,外部 p 不受影響。

三種修正方案

方案一:雙重指針(傳統 C)

void strcnp(char *sd, char **pds) {
    *pds = malloc(strlen(sd) + 1);
    strcpy(*pds, sd);
}

// 調用
char *p = NULL;
strcnp(a[0], &p); // 傳遞 p 的地址
printf("%s", p);
free(p);

方案二:返回新指針(現代風格)

char* strdup_new(const char *src) {
    char *dst = malloc(strlen(src) + 1);
    if (dst) strcpy(dst, src);
    return dst;
}

// 調用
char *p = strdup_new(a[0]);
printf("%s", p);
free(p);

方案三:呼叫端分配,函數填充(最安全)

void strcnp(const char *sd, char *ds, size_t ds_size) {
    strncpy(ds, sd, ds_size - 1);
    ds[ds_size - 1] = '\0';
}

// 調用
char buf[256];
strcnp(a[0], buf, sizeof(buf));

記憶口訣

「一級指針傳值,改指向不生效;要改指向傳二級,或直接返回新指針。」
  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved