[英]Array in C struct, pointer to constant
我有以下代碼:
typedef struct{
char *name;
int age;
} person;
int main(){
person Peter = {"peter", 19};
person Petercp = Peter;
Peter.name[0] = 'a';
Petercp.name = "hello";
printf("%s %d\n", Peter.name, Peter.age);
printf("%s %d\n", Petercp.name, Petercp.age);
}
編譯器給我該行的“錯誤訪問”錯誤消息
Peter.name[0] = 'a'
但以下行似乎很好
Petercp.name = "hello";
好像person.name數組是指向常量的指針。 我得出結論正確嗎?
而且,如果我聲明結構內部的數組為
char name[];
我再次被允許為
Peter.name[0] = 'a'
這是為什么?
當您person Peter = {"peter", 19};
,則將name
指向字符串文字“ peter”。
Peter.name[0] = 'a'
嘗試更改name
所指向的1.元素。 修改字符串文字是未定義的行為,在您的情況下會導致崩潰。 實際上,字符串文字常被加載到內存的只讀部分中。
另一方面,執行Petercp.name = "hello";
只需將指針更改為指向其他位置即可。
如果將名稱成員聲明為char name[64]
則初始化器
person Peter = {"peter", 19};
將字符串“ peter”復制到name
數組中。 名稱數組只是一個普通的char數組,您可以在其中更改各個元素。
因為您尚未為pet聲明任何空間,所以Peter.name [0]不存在。
當您使用常量字符串進行初始分配時,編譯器將為其分配常量字符串值,並且您無法更改常量。
以下將起作用:
int main(){
person Peter;
Peter.age = 19;
Peter.name = calloc(sizeof(*(Peter.name)),sizeof("hello")+1);
strncpy(Peter.name,"hello",sizeof("hello"));
Peter.name[0] = 'a';
printf("%s %d\n", Peter.name, Peter.age);
free(Peter.name);
}
此處的區別在於,直接的Peter.name = "hello"
使Peter.name
直接指向(const)字符串文字。 比較起來, strncpy
將從該文字復制到calloc
保留的空間
通過"NAME"
分配名稱會創建一個字符串常量,該常量被定義為常量。 因此,您不能在name
所指向的地址上進行任何更改。
它在6.7.3下的c11中
如果試圖通過使用具有非const限定類型的左值來修改以const限定類型定義的對象,則該行為是不確定的。 如果嘗試通過使用具有非揮發性限定類型的左值來引用以揮發性限定類型定義的對象,則該行為是不確定的。
Peter.name[0] = 'a'
這就是您在此行中要嘗試的。
因此,您將破壞代碼。 但是幸運的是編譯器避免了這種情況。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.