這段代碼是如何作業的?
#include <stdio.h>
#include <string.h>
int main()
{
#define NAME_LEN 10
char name[NAME_LEN 1]; // line 8
strcpy(name,"Hi"); // line 9
char (* name_ptr)[NAME_LEN 1] = & name; // line 10
printf("%s=%s\n%s=%s\n", // line 12
"name",name, // line 13
"name_ptr",name_ptr // line 14
);
}
在第 10 行之前一切都是例行公事。對我來說,第 10 行混合在一起宣告了一個char *and char [length],所以我希望有一個 10 的陣列char *(顯然,編譯器不同意,因為這有效)。當我用 編譯它時-Wall,我得到以下資訊:
$ cc -g -Wall a.C
a.C: In function ‘int main()’:
a.C:16:2: warning: format ‘%s’ expects argument of type ‘char*’, but argument 5 has type ‘char (*)[11]’ [-Wformat=]
);
我錯過了什么?
uj5u.com熱心網友回復:
char (* name_ptr)[NAME_LEN 1]
name_ptr是一個指向元素char陣列的指標NAME_LEN 1。所以char *即使它們參考了同一個物件,this指標的型別也不一樣。
最容易發現和理解差異的是指標演算法。
例子:
int main()
{
#define NAME_LEN 10
char name[NAME_LEN 1]; // line 8
strcpy(name,"Hi"); // line 9
char (* name_ptr)[NAME_LEN 1] = & name; // line 10
printf("name = %p (name 1) = %p, difference in chars = %td\n",
(void *)name, (void *)(name 1), (char *)(name 1) - (char *)name); // line 12
printf("name_ptr = %p (name_ptr 1) = %p, difference in chars = %td\n",
(void *)name_ptr, (void *)(name_ptr 1), (char *)(name_ptr 1) - (char *)name_ptr); // line 12
}
結果:
name = 0x7fff645264b5 (name 1) = 0x7fff645264b6, difference in chars = 1
name_ptr = 0x7fff645264b5 (name_ptr 1) = 0x7fff645264c0, difference in chars = 11
如您所見,指向陣列的指標將陣列的整個大小添加到初始地址。
因此,如果您想在 中使用此指標,則printf需要取消參考它:
printf("name_ptr = %s\n",name_ptr[0]);
printf("name_ptr = %s\n",*name_ptr);
uj5u.com熱心網友回復:
在 c 中,指標的型別并沒有真正改變它指向的內容。
正如 0___________ 所提到的,'s標志char*預期的(指向字符的指標)和(指向 11 長字符陣列的指標)之間的唯一區別是指標演算法。printf%schar (*)[11]
現在,您在第 10 行所做的就是char (*)[11]指出記憶體中恰好有['h', 'i', '\0']. 然后在您的 printf 呼叫中,您告訴它從該位置讀取一個字串。那里確實有一個字串,空終止和一切。
所以它向你抱怨指標型別,但它仍然按照它所說的去做,因為它在指標指向的地方擁有它需要的一切。
轉載請註明出處,本文鏈接:https://www.uj5u.com/qianduan/369772.html
