3

我是 C++ 语言的新手,我正在尝试理解指针的概念。

我有一个关于 char 指针的基本问题,

我所知道的是指针是一个存储地址值的变量,所以当我这样写时:

char * ptr = "hello";

根据我的基本知识,我认为=应该有一个地址分配给指针,但这里我们分配“hello”,它是一组字符。那是什么意思呢?
指针是否指向ptr存储“hello”的地址?还是它本身存储你好?
我很困惑,希望你们能帮助我。。

提前致谢。

4

6 回答 6

12

ptr保存文字"hello"存储的地址。在这种情况下,它指向一个字符串文字。它是位于静态(最常见的是只读)内存中的不可变字符数组。

您可以ptr通过重新分配来指出其他内容,但在您这样做之前,修改内容是非法的。(它的类型实际上是const char*,为了 C 兼容性,不推荐使用转换为char*(在 C++11 中甚至是非法的)。

因为这个保证,编译器可以自由优化空间,所以

char * ptr = "hello";
char * ptr1 = "hello";

可能会产生两个相等的指针。(即ptr == ptr1

于 2013-09-07T22:41:59.143 回答
6

指针指向存储“hello”的地址。更准确地说,它指向“hello”中的“h”。

于 2013-09-07T22:42:16.427 回答
2

"hello"是一个字符串文字:一个静态字符数组。像所有数组一样,如果在需要指针的上下文中使用它,它可以转换为指向其第一个元素的指针。

但是,数组是恒定的,因此将其分配给char*(而不是const char*)是一个非常糟糕的主意。如果您尝试使用该指针来修改字符串,您将得到未定义的行为(通常是访问冲突)。

于 2013-09-07T22:44:30.157 回答
1

编译器将“找到某个地方”它可以放置字符串"hello",并且ptr将具有那个“某处”的地址。

于 2013-09-07T22:42:42.873 回答
0

char* text = "Hello!"可以认为如下:

在程序启动时,您创建一个长度为 7 的字符数组: {'H','e','l','l','o','!','\0'}. 最后一个是空字符,表明它后面没有更多字符。[这比保持与字符串关联的计数更有效......对于 32 位整数,计数可能占用 4 个字节,而空字符只是一个字节,如果使用 Unicode 字符串则为两个字节. 另外,与必须同时管理一个字符数组和一个计数变量相比,拥有一个以空字符结尾的单个数组更容易混淆。]

创建数组和创建字符串常量之间的区别在于数组是可编辑的,而字符串常量(或“字符串文字”)不是。尝试在字符串文字中设置值会导致问题:它们是只读的。

然后,每当您调用语句时char* text = "Hello!",您都会获取该初始数组的地址并将其粘贴到变量text中。请注意,如果你有这样的事情......

char* text1 = "Hello!";
char* text2 = "Hello!";
char* text3 = "Hello!";

...那么很可能您正在创建三个单独的数组{'H','e','l','l','o','!','\0'},因此这样做会更有效...

char* _text = "Hello!";
char* text1 = _text;
char* text2 = _text;
char* text3 = _text;

大多数编译器足够聪明,只能自动初始化一个字符串常量,但有些编译器只有在您手动打开某些优化功能时才会这样做。

另一个注意事项:根据我的经验,使用delete []指向字符串文字的指针不会引起问题,但这是不必要的,因为据我所知它实际上并没有删除它。

于 2013-09-07T23:09:34.580 回答
0

当您通过为其分配字符串文字来创建新的 char* 时,会发生 char* 被分配文字的地址。所以 char* 的实际值可能是 0x87F2F1A6 (一些十六进制地址值)。char* 指向字符串的开头(在本例中为第一个字符)。在 C 和 C++ 中,所有字符串都以 /0 结尾,这是系统知道它已到达字符串末尾的方式。

于 2013-09-07T22:45:39.790 回答