何时使用const char *以及何时使用const char
我知道他们是不同的,我知道他们是如何不同,我读了所有问题,我可以find关于char*
vs char[]
但是,所有这些答案永远不会告诉他们何时应该使用。
所以我的问题是:
你什么时候用
const char *text = "text";
你什么时候用
const char text[] = "text";
有没有任何指导原则或规则?
举个例子,哪一个更好:
void withPointer() { const char *sz = "hello"; std::cout << sz << std::endl; } void withArray() { const char sz[] = "hello"; std::cout << sz << std::endl; }
(我知道std::string
也是一个选项,但我特别想知道关于char
指针/数组)
两者截然不同,首先:
- 第一个创build一个指针。
- 第二个创build一个数组。
阅读更详细的解释:
arrays版本:
char text[] = "text";
创build一个足够大的数组来保存string文本“text”,包括NULL
终止符。 数组text
是用string文字“text”初始化的。 该数组可以稍后修改 。 此外,数组的大小即使在编译时也是已知的,所以sizeof
运算符可以用来确定它的大小。
指针版本:
char *text = "text";
创build一个指向string文字“text”的指针。 这比数组版本快, 但指针指向的string不应该改变 ,因为它位于只读实现定义的内存中。 修改这样的string会导致未定义的行为 。
事实上,C ++ 03不赞成使用不带const
关键字的string。 所以声明应该是:
const char*text = "text";
另外,你需要使用strlen()
函数,而不是sizeof
来查找string的大小,因为sizeof
运算符只会给你指针variables的大小。
哪个版本更好?
取决于使用情况。
- 如果不需要对string进行任何更改,请使用指针版本。
- 如果您打算更改数据,请使用arrays版本。
编辑:它刚刚被带到我注意到(在评论中)OP寻求区别:
const char text[]
和const char* text
那么以上的不同点仍然适用,除了修改string文字。 使用const
限定符,数组test
现在是一个包含const char
types元素的数组,这意味着它们不能被修改。
鉴于此,我会select指针版本的数组版本,因为指针可以(错误地)重新设置为另一个指针,并且可以通过另一个指针来修改string,从而产生UB。
也许最大的区别是你不能使用sizeof
运算符的指针来获取开始指向的缓冲区的大小,在const char[]
版本中,你可以使用sizeof
对数组variables来获得内存占用的大小数组的字节数。 所以这真的取决于你想要做什么 – 用指针或缓冲区,以及如何使用它。
例如,做:
void withPointer() { const char *sz = "hello"; std::cout << sizeof(sz) << std::endl; } void withArray() { const char sz[] = "hello"; std::cout << sizeof(sz) << std::endl; }
会给你非常不同的答案。
一般来说,要回答这些types的问题,请使用最明确的问题 。
在这种情况下, const char[]
获胜是因为它包含更多关于数据的详细信息,即缓冲区的大小。
只是一个说明:
我会使它static const char sz[] = "hello";
。 声明这样做有一个很好的优势,就是通过写入只读内存来更改该常量string,从而使程序崩溃。 如果没有static
,抛弃常量然后改变内容可能会被忽视。
此外, static
使数组简单地位于常量数据部分,而不是在堆栈上创build,并在每次调用该函数时从常量数据部分复制。
如果使用数组,则数据在运行时被初始化。 如果使用指针,运行时开销可能会减less,因为只有指针需要被初始化。 (如果数据小于指针的大小,那么数据的运行时初始化小于指针的初始化。)因此,如果您有足够的数据,那么您关心运行时初始化的成本,你应该使用一个指针。 你几乎不应该关心这些细节。
几年前,Ulrich Drepper的博客文章给了我很多帮助:
如此接近,但没有雪茄和更多的arrays乐趣
博客的要点是, const char[]
应该是首选,但只能作为全局或静态variables。
使用指针const char*
有一个缺点:
- 一个额外的variables
- 指针是可写的
- 一个额外的间接
- 通过指针访问string需要2个内存加载