C++ 中关于 char* 的困惑

teq*_*ila 1 c++ pointers char

测试代码:

#include <iostream>
using namespace std;
int main()
{
    const char* b="str";
    cout << b << endl;
    cout << *b << endl;
    cout << &b << endl;
    cout << *(&b) << endl;
    
    
    return 0;
}
Run Code Online (Sandbox Code Playgroud)

结果:

str
s
0x7ffdf39c27f0
str
Run Code Online (Sandbox Code Playgroud)

我在 web runoob 在线编译器上运行我的代码

为什么我会得到这些结果?我查看了一些有关 char* 的问题,但不足以让我理解。有人可以向我解释一下吗?图片最好。

我想通过推荐的书籍或博客了解更多信息。

顺便说一句,使用char b[]代替const char*,我得到了相同的结果。


非常感谢大家。

我只是想知道为什么 char 指针的值不是地址。

我认为地址类似于 0x7ffdf39c27f0。一个内存地址。

const char* b = "str"。b 就是str.

我发现这*b与 相同*("str")

所以我想知道记忆里到底发生了什么?为什么 char 指针的值不是地址?

Pet*_*ter 5

要了解代码输出的内容,您需要了解 C++ 输出流(类型为 的对象std::ostream),因此对象(例如std::cout)具有许多operator<<(). 调用的重载取决于提供的参数类型。

我将解释您的第二个示例,但第一个示例的解释几乎相同。

const char* b="st\0r";
cout << b << endl;
cout << *b << endl;
cout << &b << endl;
cout << *(&b) << endl;
Run Code Online (Sandbox Code Playgroud)

cout << b扩展到有 type 的cout.operator<<(b)地方。运算符函数的重载假定参数指向以 null 结尾的字符串(的第一个字符),该字符串在内存中表示为以with 值(零)结尾的数组。运算符函数输出它找到的每个字符,直到到达一个字符。第一个找到的是您在 后显式插入的那个,因此生成了输出。事实上,你的字符串在 后面有第二个是无关紧要的,因为运算符函数在它找到的第一个字符串处停止。bconst char *charchar'\0''\0''\0''t'st'\0''r'

cout << *boperator<<()扩展为对接受单个的不同重载的调用char,并输出该char*b是 表示的字符串中第一个字符的值b。这样就产生了输出s

cout << &b,中&b具有类型const char ** 或 (等效地)char const **。不存在operator<<()接受 a 的输出流的重载const char **,但存在接受 a 的重载const void *。由于任何指针(指向成员的指针或指向函数的指针除外)都可以隐式转换为void *,因此该转换是由编译器执行的,因此重载匹配并被调用。该特定的重载会operator<<()打印内存中的地址。

第三种情况下的隐式转换不会在前两种情况下发生,因为不需要隐式转换的调用比需要隐式转换的调用更匹配。

最后一条语句*(&b)相当于b. 出现这种情况是因为&此代码中的 是取址运算符,而 是*取消引用运算符(它是取址运算符的逆运算符)。因此最后一条语句产生与 相同的输出cout << b