繁体   English   中英

std::string 和 int 的串联会导致转变。 为什么?

[英]Concatenation of std::string and int leads to a shift. Why?

今天,当我尝试将std::stringint连接时,我感到很惊讶。 考虑以下 MWE:

#include <iostream>
#include <string>

void print(const std::string& text)
{
    std::cout << "The string is: " << text << ".\n";
}

int main()
{
    print("iteration_" + 1);

    return 0;
}

而不是打印

The string is: iteration_1.

我希望,它打印

The string is: teration_.

后台到底发生了什么? 字符串是否由于某种原因被转换为char[]或类似的东西? operator+ 的文档没有列出任何带有std::stringint的内容。

std::string与数字连接的正确方法是什么? 我真的必须将它们都放入std::stringstream或使用std::to_string()将数字显式转换为std::string吗?

这条线是问题所在:

print("iteration_" + 1);

字符串文字正在衰减为char* 您正在向此char*添加1 ,将其移动到下一个字符。

如果您想将字符串"1"添加到文字的末尾,一种相当简单的方法是将字符串文字传递给std::string构造函数并手动将1转换为字符串。 例如:

print(std::string("iteration_") + std::to_string(1));

字符串是否由于某种原因被转换为 char[]

事实上,情况恰恰相反。 "iteration_"是一个char[11] ,当您添加1时它会衰减为const char* 将指针加一使其指向字符串中的下一个字符。 然后使用它来构造一个临时的std::string ,它包含除第一个字符之外的所有字符。

您链接的文档适用于std::stringoperator+ ,但要使用它,您首先需要std::string

"iteration_"不是std::string ,而是const char[] 衰减到const char* ,而"iteration_" + 1只是执行指针算术并将指针移动到下一个char (即't' ),然后你就得到了 c 风格的字符串"teration_"

您可以使用std::to_stringint转换为std::string ,然后将它们连接起来。 例如

print("iteration_" + std::to_string(1));

对于这种情况,调用std::operator+(std::basic_string)并将第一个参数"iteration_"隐式转换为std::string然后传递给operator+ ,然后将连接的std::string传递给print

居住

如果您尝试使用以下内容:

std::string str = "iteration" + 1;

编译器会抛出警告:

警告:将“int”添加到字符串不会 append 到字符串 [-Wstring-plus-int]

这是因为您将指向“迭代”字符串的指针增加 1,这意味着现在“迭代”字符串被分配给str变量。

连接的正确方法是:

std::string str = "iteration" + std::to_string(1);

表达式"iteration_" + 1是添加到int 1 的const char[11]文字。

在该表达式中, "iteration_"衰减为指向数组第一个元素的const char*指针 + 1然后发生在该指针的指针算术中。 整个表达式的计算结果为const char*类型(指向第一个t ),它是std::string构造函数的有效 NUL 终止输入! (匿名临时std::string绑定const std::string& function 参数。)

这是完全有效的 C++,偶尔可以很好地使用。

如果您想将+视为串联,则

print("iteration_" + std::to_string(1));

是一种方式。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM