2010-08-13 51 views
7

爲什麼下面的代碼是非法的?c中的字符串字面值

typedef struct{ 
    char a[6]; 
} point; 

int main() 
{ 
    point p; 
    p.a = "onetwo"; 
} 

它與文字的大小有什麼關係?或者在聲明後將字符串文字分配給char數組只是非法的?

+0

可能重複(http://stackoverflow.com/questions/579734/assigning-strings-to-arrays-of-characters) – 2010-08-13 04:06:53

+0

不完全是重複的,因爲這是一個包含字符數組的結構,它與常規字符數組略有區別,我在我的回答中已經解釋了這一點。 – dreamlax 2010-08-13 04:51:55

回答

11

它與尺寸沒有任何關係。在創建字符數組後,您不能將字符串文字分配給字符數組 - 您只能在定義時使用它。

當你

char a[] = "something"; 

它創造足夠的大小(包括終止空)的數組和複製的字符串數組。在用字符串文字初始化數組大小時指定數組大小並不是一個好習慣 - 您可能不會考慮空字符。

當你

char a[10]; 
a = "something"; 

你想分配給數組,這是違法的地址。

編輯:正如在其他答案中所提到的,你可以做一個strcpy/strncpy,但要確保數組是用所需長度初始化的。

strcpy(p.a, "12345");//give space for the \0 
6

在創建數組後,您決不能分配給數組;這同樣是非法的:

int foo[4]; 
int bar[4]; 
foo = bar; 

您需要使用指針或分配給數組的索引;這是合法的:

p.a[0] = 'o'; 

如果你想離開它在結構數組,你可以使用函數像strcpy

strncpy(p.a, "onetwo", 6); 

(注意字符數組必須足夠大持有NUL終止符,所以你可能想使它char a[7]和最後一個參數strncpy改爲7)

+1

我想我應該感到高興,我的'strcpy'解決方案編輯的每個答案 – 2010-08-13 04:35:01

+0

在這裏,有一個+1。如果可以的話,我會+2,但是我覺得有點奇怪,沒有人注意到這是一個包含數組的struct,而不僅僅是一個普通的數組。 – dreamlax 2010-08-13 04:56:39

+0

當然,「strncpy」帶有自己的問題,與大多數其他「n」功能不同。 – 2010-08-13 17:29:24

6

數組是non modifiable lvalues。所以你不能分配給他們。賦值運算符的左側必須是modifiable lvalue

但是,您可以在定義數組時對其進行初始化。

例如:

char a[] = "Hello World" ;// this is legal 
char a[]={'H','e','l','l','o',' ','W','o','r','l','d','\0'};//this is also legal 

//but 

char a[20]; 
a = "Hello World" ;// is illegal 

但是你可以使用strncpy(a, "Hello World",20);

+2

如果在數組是'defined'(而不是'聲明')時使用了正確的術語'initialize'而不是'assign',那將會更清楚。 – 2010-08-13 04:20:27

+2

@喬納森:是的,你是正確的。固定! :) – 2010-08-13 04:25:04

1

注意的是,爲了存儲字符串「ONETWO」你的數組中,它必須是長度[7],而不是正如問題中所寫的那樣。額外的字符用於存儲'\ 0'終止符。

3

正如其他答案已經指出,你只能用字符串文字初始化一個字符數組,你不能將一個字符串文字分配給一個字符數組。然而,結構(甚至包含字符數組的那些)是另一個魚羣。

我不會建議在實際程序中這樣做,但這表明雖然數組類型不能分配給,但包含數組類型的結構可以。

typedef struct 
{ 
    char value[100]; 
} string; 

int main() 
{ 
    string a = {"hello"}; 
    a = (string){"another string!"}; // overwrite value with a new string 
    puts(a.value); 

    string b = {"a NEW string"}; 
    b = a; // override with the value of another "string" struct 
    puts(b.value); // prints "another string!" again 
} 

因此,在你原來的例子,下面的代碼應該細編譯:

typedef struct{ 
    char a[6]; 
} point; 

int main() 
{ 
    point p; 

    // note that only 5 characters + 1 for '\0' will fit in a char[6] array. 
    p = (point){"onetw"}; 
} 
+0

對於'struct'的例子+1,但是請注意這些複合文字是C99的附加。 (同樣適用於'//'樣式的評論。) – schot 2010-08-13 06:25:22

1

沒有的strcpy或C99複方文字是必要的。在純ANSI C的例子:[分配字符串字符數組]的

typedef struct{ 
    char a[6]; 
} point; 

int main() 
{ 
    point p; 
    *(point*)p.a = *(point*)"onetwo"; 
    fwrite(p.a,6,1,stdout);fflush(stdout); 
    return 0; 
}