C - 为什么strcpy()是必需的

C_p*_*678 27 c string strcpy

有人可以向我解释为什么strcpy()是将字符串分配给字符数组所必需的,例如在下面的代码片段中.

int main(void) {

char s[4];

s = "abc"; //Fails
strcpy(s, "abc"); //Succeeds

return 0;
}
Run Code Online (Sandbox Code Playgroud)

s = "abc"失败的原因是什么?为什么strcpy()是在声明字符串后将字符串赋值给char数组的唯一方法?我似乎很奇怪你必须使用一个函数来执行一个基本的赋值.

AnT*_*AnT 30

C中的数组是不可赋值和非可复制初始化的.这就是数组如何在C中.历史上,在值上下文中(在赋值的RHS上)数组衰减为指针,这正式地阻止了赋值和复制初始化.这适用于所有阵列,不仅适用于char阵列.

C语言从其前身--B和BCPL语言继承了这种数组行为.在这些语言中,数组由物理指针表示.(显然,当你将一个数组分配给另一个数组时,指针的重新分配并不是你想要发生的.)在C语言中,数组不是指针,但它们通过衰减"模拟"B和BCPL数​​组的历史行为.在大多数情况下指向.这一历史遗产使C阵列至今无法复制.

上面的一个例外是使用字符串文字进行初始化.你可以做到

char c[] = "abc";
Run Code Online (Sandbox Code Playgroud)

但就是这样.

这意味着无论何时要复制数组,都必须使用库级存储器复制功能"abc".c只是一种专门用于弦乐的风格.


cni*_*tar 13

这就是C中的数组.您无法分配它们.如果您愿意,可以使用指针:

char *p;
p = "abc";
Run Code Online (Sandbox Code Playgroud)

顺便提一下,有一个C FAQ.

数组是C中的"二等公民"; 这种偏见的一个结果就是你无法分配给他们.

  • @ C_p678 - 不,`s`是一个char数组,"abc"是一个指向常量字符串的指针. (4认同)
  • @MByD:不完全正确.`"abc"`不是指针.`"abc"`类型为`char [4]`的数组,在此上下文中衰减为类型为`char*`的指针.注意,在C中,字符串不是常量.它是不可修改的,但类型本身不包括`const`限定符. (3认同)
  • @AndryT:更挑剔的是,"常量"和"常量"是两个非常不同的东西."const"可能应该被称为"readonly".常量或常量表达式是可以在编译时进行评估的表达式; const对象是在运行时无法修改的对象.考虑`const int r = rand();`. (2认同)