以下功能使用const char *s1
该功能的作用可能并不重要。如果是字符串,则返回1 包含允许的字符以外的字符。如果它返回0 没有。
int TEST (const char *s1);
int TEST (const char *s1) {
char * s2= "o123";
return s1[ strspn(s1, s2) ] != '\0';
}
如果我要从中移除const
部分,该函数似乎工作正常。
为什么我在该函数中需要const
术语,如果它没有它可以正常工作?它的重要性是什么?
答案 0 :(得分:3)
当你有const char *s1
时,你告诉编译器你不会修改s1
指向的内存的内容。它是编译器的语义信号,因此您不会在函数中出错(尝试更改内容将导致错误)。它还可能允许编译器添加一些优化。
但更重要的是,它是其他程序员阅读代码和使用您的函数的信号。对于“其他程序员”,我还会在几周,几个月或几年内包含你,当你回到代码并忘记了它的细节时。
答案 1 :(得分:2)
“const”的重要性?
3个理由:
实用性
代码正确性
速度
考虑允许调用代码执行的操作
int TEST_with_const(const char *s1);
int TEST_without_const(char *s1);
char *cs;
const char *ccs
...
TEST_with_const(cs); // allowed
TEST_with_const(ccs); // allowed
TEST_without_const(cs); // allowed
TEST_without_const(ccs); // fails to compile.
最后一个失败是因为TEST_without_const(char *s1);
告诉外面的世界,我想要一个指向我可能改变的内存的指针。 ccs
不是指向可修改内存的指针。
假设TEST_without_const(char *s1);
具有相同的int TEST (const char *s1)
主体,则它不需要指向可修改内存的指针
通过使用const char *s1
,函数的主体会在编译期间抱怨,如果尝试修改s1
指向的内存。如果函数设计不需要修改s1
指向的内存,则此检查有助于确保正确性。
根据编译器的不同,const char *
可以进行一些优化,但char *
不能进行优化。
答案 2 :(得分:1)
const
会阻止您在变量指向的内存中写入内容。
在这里,您只检查值是否等于\0
并且它是正常的,因为您只读取操作。
int TEST (const char *s1) {
char * s2= "o123";
return s1[ strspn(s1, s2) ] != '\0';
}
如果你这样做,试着写一下s1
指针:
int TEST (const char *s1) {
char * s2= "o123";
s1[0] = '4'; //Error, s1 is const pointer, can't write to memory pointed to by s1
return s1[ strspn(s1, s2) ] != '\0';
}
你的情况下的 const
指针意味着这个函数should not
将任何数据写入输入指针,只能执行读操作。实际上,您可以更改s1
点的位置,但不允许通过s1
写入内存。这是为了防止任何错误现在意外写入,因为它可能在某些情况下导致未定义的行为。
答案 3 :(得分:1)
使用const
会阻止您或其他人使用您的代码做出意外错误的事情。此外,它是出于文档目的,因为代码的读者知道这些函数不会改变指针所指向的字符(只读)。
此外,如果您使用const
正确性,编译器可能会优化您的代码,因为它知道这些值在只读函数内部没有变化。但记录和使您的功能更安全的第一个原因更重要。
您总会遇到三种形式:char* s1
,const char* s1
和const char* const s1
。第四个但很少需要的形式是:char* const
。含义如下:
<强> 1。
char* s1
强>
在这种情况下,s1
只是指针到一个或多个字符的内存。
以下内容可以/不能在函数内部完成:
/* Function might changes content of s1 */
int TEST (char* s1)
{
s1[0] = 'A'; /* works */
*s1 = 'A'; /* same as above works */
++s1; /* this works because the copy of the pointer is non constant */
...
}
可以/不能进行以下调用:
char* str;
const char* const_str;
...
TEST(str); /* works as str as no restrictions */
TEST(const_str); /* fails because function might change const const_str */
<强> 2。
const char* s1
强>
术语:const char* s1
表示s1
是指针到一个或多个字符的内存,无法使用此指针进行更改 。以下内容可以/不能在函数内部完成:
/* Function is read-only and doesn't changes content of s1 */
int CONST_TEST (const char* s1)
{
s1[0] = 'A'; /* compiler fail */
*s1 = 'A'; /* same as above compiler fail */
++s1; /* this works because the copy of the pointer is non constant */
...
}
可以/不能进行以下调用:
char* str;
const char* const_str;
...
CONST_TEST(str); /* works as str as no restrictions */
CONST_TEST(const_str); /* works because function is read-only and const_str is it also */
编译器将无法编译并告诉您尝试写入标记为常量的内存位置。
第3。
const char* const s1
强>
这意味着:s1
是一个常量指针到一个或多个字符的内存,无法使用此指针进行更改。这是第一种方法的扩展,指针s1
本身是按值传递的,而且这个副本不能在函数内部进行更改。因此,您可以不在函数内部执行类似++s1
的操作,因此指针将始终指向相同的内存位置。
<强> 4。
char* const s1
强>
这类似于案例3,但没有s1
指向标记为常量的内存。因此,指向的内容s1
可以像情况1一样改变,但指针是常量。