C 字符指针赋值矩之间的差异
今天有人告诉我,这个代码:C 字符指针赋值矩之间的差异,c,c-strings,C,C Strings,今天有人告诉我,这个代码: int main(){ char *a; a = "foobar"; /* a used later to strcpy */ return 0; } 是不好的,可能会导致问题和错误。 然而,我的代码没有任何问题,我不明白,这和 int main(){ char *a = "foobar"; /* a used later to strcpy */ return 0; } 我认为这是“正确的”方法。 有人能描述一下,为什么这两种代码是不同的吗? 如果
int main(){
char *a;
a = "foobar";
/* a used later to strcpy */
return 0;
}
是不好的,可能会导致问题和错误。
然而,我的代码没有任何问题,我不明白,这和
int main(){
char *a = "foobar";
/* a used later to strcpy */
return 0;
}
我认为这是“正确的”方法。
有人能描述一下,为什么这两种代码是不同的吗?
如果第一个可能有问题,请举例说明 在功能上,它们是相同的 在前一个代码段中,
a
被分配给字符串文本;在后者中,a
用字符串文本初始化。
在这两种情况下,a
指向字符串文字(不能修改)
没有理由认为一个比另一个更正确。我更喜欢后者,但那只是我个人的喜好。从功能上讲,它们是一样的 在前一个代码段中,
a
被分配给字符串文本;在后者中,a
用字符串文本初始化。
在这两种情况下,a
指向字符串文字(不能修改)
没有理由认为一个比另一个更正确。我更喜欢后者,但这只是我个人的偏好。两个代码段都同样糟糕,因为它们都以指向常量数据的非常量指针结尾。如果使用非常量指针(尝试)更改数据,您将获得未定义的行为:从它工作到程序崩溃,一切都可能发生,包括忽略修改指令 正确的方法是使用常量指针或初始化非常量数组
const char *a = "foobar";
或
但请注意,在后一种情况下,您有一个真正的数组而不是指针,因此如果您确实需要指针语义,也可以这样做:
char _a[] = "foobar";
char *a = _a;
这两个代码段都同样糟糕,因为它们都以指向常量数据的非常量指针结尾。如果使用非常量指针(尝试)更改数据,您将获得未定义的行为:从它工作到程序崩溃,一切都可能发生,包括忽略修改指令 正确的方法是使用常量指针或初始化非常量数组
const char *a = "foobar";
或
但请注意,在后一种情况下,您有一个真正的数组而不是指针,因此如果您确实需要指针语义,也可以这样做:
char _a[] = "foobar";
char *a = _a;
有些地方有编码标准,例如通过Coverity等工具帮助进行静态代码分析 我在几个地方看到的一个编码实践规则是,变量应该总是被声明为初始化的,以简化事情,使分析更容易 第二个代码段比第一个代码段更接近该规则,因为不可能在未初始化的情况下插入新代码
在代码维护方面,这是一个积极的好处。有些地方有编码标准,例如通过Coverity等工具帮助进行静态代码分析 我在几个地方看到的一个编码实践规则是,变量应该总是被声明为初始化的,以简化事情,使分析更容易 第二个代码段比第一个代码段更接近该规则,因为不可能在未初始化的情况下插入新代码
对于代码维护来说,这是一个积极的好处。为什么您认为第一个比第二个更糟糕?它们同样糟糕,因为指针不是常量。
strcpy()
中的a
是如何使用的?当然不是作为目标;)我没有使用const,因为我用的是比ansic更早的C语言编写代码,还没有const
关键字。为什么你认为第一个比第二个更糟糕?它们同样糟糕,因为指针不是常量。strcpy()
中的a
是如何使用的?当然不是作为目标;)我没有使用const,因为我是用C编写代码的,比ANSI C早,还没有const
关键字。我没有使用const
关键字,因为我用C编写了这段代码,const出现在C89中,在大学里他们教我们更旧的标准,我只是从那里复制了我的代码。@Kaznov我的回答确实假设了一个相当新的C版本:-)。我已经足够大了,记得原来的K&R C。。。在那些旧版本中,stringliteral是可修改的,您的代码是正确的。但是,如果你必须生成真实的代码,你就必须迅速改变这些编码实践……我没有使用const
关键字,因为我用普通的C编写了这段代码,const出现在C89中,在大学里,他们教给我们更旧的标准,我只是从那里复制了我的代码。@Kaznov我的答案确实假设了一个相当新的C版本:-)。我已经足够大了,记得原来的K&R C。。。在那些旧版本中,stringliteral是可修改的,您的代码是正确的。但是,如果您必须生成真实的代码,那么您必须快速更改这些编码实践。。。