临时对象中的字符串文字?
String Literal in the temporary object?
我是 C++ 及其底层的初学者(与 Python 等相比)。我在 Whosebug 上读到字符串文字进入只读数据部分 (String literals: Where do they go?),但目前我正在阅读一本 C++ 书(作者 Bjarne Stroustrup),里面写到临时对象的生命结束于表达式的结尾,所以:
string var1 = "Hello ";
string var2 = "World";
string var3 = var1 + var2; // string temp = "Hello World" and assign it to var3
执行后,我们会留下两个 "Hello World"
还是只剩下一个个副本?
硬件:
OS: Windows 11;
Compiler: MSVC;
Standard: C++11
我知道它可能是实现定义的,但如果是这样,请针对 x86 平台指定。
字符串文字是用语法
专门引用的对象
"Hello "
或
"World"
这就是 literal 的意思,一个值的原子语法。它一般不指字符串值。
字符串文字不是临时对象。它们是以未指定的方式存储的对象(实际上,如您所指出的,通常在 read-only 内存中)并且具有 静态存储持续时间 ,这意味着它们在完整的持续时间内存在程序执行。
当你写作时
string var1 = "Hello ";
您正在创建一个 std::string
对象,该对象是从字符串文字初始化的。它本身既不是字符串文字,也不保存或引用字符串文字。它会简单地将文字中的字符复制到它自己管理的一些存储中。 var1
对象(如果在块范围内声明,即在函数内)具有 自动存储持续时间 ,这意味着它一直存在到声明它的范围结束为止。
行
string var3 = var1 + var2;
用于(在 C++17 之前)创建临时 std::string
对象,该对象由 +
return 编辑std::string
的运算符重载。然后 var3
是来自这个临时文件的 move-constructed。 var1 + var2
产生的临时值将一直存在到 完整表达式的末尾 ,这意味着直到 var3
的初始化完成。
但是,从 C++17 开始,这里不再涉及临时变量。相反,+
运算符重载将直接构造 var3
对象。在 C++17 之前,这也被允许发生,因为 so-called return 值优化.
因此,在您的代码中,不存在任何 "Hello World"
字符串文字,但恰好存在一个包含字符 Hello World
的 string
对象,如果您是使用 pre-C++17 版本,可能 还有一个临时 std::string
对象,它具有相同的值,但在 [=19 初始化后被销毁=].
我是 C++ 及其底层的初学者(与 Python 等相比)。我在 Whosebug 上读到字符串文字进入只读数据部分 (String literals: Where do they go?),但目前我正在阅读一本 C++ 书(作者 Bjarne Stroustrup),里面写到临时对象的生命结束于表达式的结尾,所以:
string var1 = "Hello ";
string var2 = "World";
string var3 = var1 + var2; // string temp = "Hello World" and assign it to var3
执行后,我们会留下两个 "Hello World"
还是只剩下一个个副本?
硬件:
OS: Windows 11;
Compiler: MSVC;
Standard: C++11
我知道它可能是实现定义的,但如果是这样,请针对 x86 平台指定。
字符串文字是用语法
专门引用的对象"Hello "
或
"World"
这就是 literal 的意思,一个值的原子语法。它一般不指字符串值。
字符串文字不是临时对象。它们是以未指定的方式存储的对象(实际上,如您所指出的,通常在 read-only 内存中)并且具有 静态存储持续时间 ,这意味着它们在完整的持续时间内存在程序执行。
当你写作时
string var1 = "Hello ";
您正在创建一个 std::string
对象,该对象是从字符串文字初始化的。它本身既不是字符串文字,也不保存或引用字符串文字。它会简单地将文字中的字符复制到它自己管理的一些存储中。 var1
对象(如果在块范围内声明,即在函数内)具有 自动存储持续时间 ,这意味着它一直存在到声明它的范围结束为止。
行
string var3 = var1 + var2;
用于(在 C++17 之前)创建临时 std::string
对象,该对象由 +
return 编辑std::string
的运算符重载。然后 var3
是来自这个临时文件的 move-constructed。 var1 + var2
产生的临时值将一直存在到 完整表达式的末尾 ,这意味着直到 var3
的初始化完成。
但是,从 C++17 开始,这里不再涉及临时变量。相反,+
运算符重载将直接构造 var3
对象。在 C++17 之前,这也被允许发生,因为 so-called return 值优化.
因此,在您的代码中,不存在任何 "Hello World"
字符串文字,但恰好存在一个包含字符 Hello World
的 string
对象,如果您是使用 pre-C++17 版本,可能 还有一个临时 std::string
对象,它具有相同的值,但在 [=19 初始化后被销毁=].