C++ '+' 连接运算符更改指针向量中指针的内容
C++ '+' concatenation operator changing contents of pointers in pointer vector
所以我想编写一个程序来执行以下操作:
- 使用std::getline(std::cin,str)
接受用户输入的字符串
- 使用
+
运算符将此输入附加到 std::string object
object
的初始值为object="\n"
- 用户输入一行并附加到
object
后,将 '\n'
添加到对象
- 例如,如果在控制台中输入
hello
,则 object="\nhello\n"
- 如果在下一行输入
my
,则 object="\nhello\nmy\n"
,依此类推。
现在我还声明了一个 std::vector<const char*> lines
指向 object
中的所有 \n
个字符
在我们以最后一个要点中给出的示例为例,lines
有 3 个元素指向 \n
个字符
代码如下:
#include <iostream>
#include <string>
#include <vector>
int main()
{
std::vector<const char*> lines;
std::string object = "\n";
lines.push_back(object.c_str());
std::string temp;
int object_size;
while (std::getline(std::cin,temp))
{
object_size = object.length();
object = object + temp;
object = object + "\n";
lines.push_back(object.c_str() + object_size + temp.size());//pointers in this point to all the \n characters
}
}
现在进入问题:
所以输入后
hello
name
is
并在 vs 2019 集成调试器的 watch window 中检查行和对象的值,它显示
object="\nhello\nname\nis\n"
lines[0]=0x0082fb04"\nhello\nname\nis\n" \points to first \n
lines[1]=0x0082fb0a"\nname\nis\n" \points to second \n
lines[2]=0x0082fb0f"\nis\n" \points to third \n
lines[3]=0x0082fb12"\n" \points to last \n
这是有道理的,因为 object
中有 4 个 \n
。
现在我在下一行输入 xyzabc
,所以控制台看起来像:
hello
name
is
xyzabc
在 while 循环中,一切正常,直到行
object=object+temp;
一执行object=object+temp;
,调试器就显示:
object="\nhello\nname\nis\nxyzabc" \object does not end with \n because object = object + "\n" has not been executed yet
lines[0]=0x0082fb04 "pù\x4\x1lo\nname\nis"
lines[1]=0x0082fb0a "\nname\nis"
lines[2]=0x0082fb1f "\nis"
lines[3]=0x0082fb12""
object
的值符合预期,但 lines
中的指针指向的内容已被 object=object+temp
行修改
执行该行后的预期值为:
object="\nhello\nname\nis\nxyzabc"
lines[0]=0x0082fb04"\nhello\nname\nis\nxyzabc"
lines[1]=0x0082fb0a"\nname\nis\nxyzabc"
lines[2]=0x0082fb0f"\nis\nxyzabc"
lines[3]=0x0082fb12"\nxyzabc"
为什么会这样?以及如何附加 I object
和 temp
而不会遇到这个问题?
object + temp;
和 object + "\n";
都很好并且做正确的事情:连接字符串。但是,这是不正确的:
lines.push_back(object.c_str() + object_size + temp.size());
因为 (cppreference::string::c_str)...
Returns a pointer to a null-terminated character array with data
equivalent to those stored in the string.
The pointer is such that the range [c_str(); c_str() + size()] is
valid and the values in it correspond to the values stored in the
string with an additional null character after the last position.
The pointer obtained from c_str() may be invalidated by:
- Passing a non-const reference to the string to any standard library function, or
- Calling non-const member functions on the string, excluding operator[], at(), front(), back(), begin(), rbegin(), end() and
rend().
从 c_str
返回的指针不应该独立于字符串存储。如果你想在向量中存储字符串(而不是无效的指针)你应该使用 std::vector<std::string>
.
object
可能会在您将内容连接到其中时重新分配。这意味着指向其在 lines
中的内容的指针无效。那是未定义的行为。
所以我想编写一个程序来执行以下操作:
- 使用std::getline(std::cin,str) 接受用户输入的字符串
- 使用
+
运算符将此输入附加到std::string object
object
的初始值为object="\n"
- 用户输入一行并附加到
object
后,将'\n'
添加到对象 - 例如,如果在控制台中输入
hello
,则object="\nhello\n"
- 如果在下一行输入
my
,则object="\nhello\nmy\n"
,依此类推。
现在我还声明了一个 std::vector<const char*> lines
指向 object
\n
个字符
在我们以最后一个要点中给出的示例为例,lines
有 3 个元素指向 \n
个字符
代码如下:
#include <iostream>
#include <string>
#include <vector>
int main()
{
std::vector<const char*> lines;
std::string object = "\n";
lines.push_back(object.c_str());
std::string temp;
int object_size;
while (std::getline(std::cin,temp))
{
object_size = object.length();
object = object + temp;
object = object + "\n";
lines.push_back(object.c_str() + object_size + temp.size());//pointers in this point to all the \n characters
}
}
现在进入问题:
所以输入后
hello
name
is
并在 vs 2019 集成调试器的 watch window 中检查行和对象的值,它显示
object="\nhello\nname\nis\n"
lines[0]=0x0082fb04"\nhello\nname\nis\n" \points to first \n
lines[1]=0x0082fb0a"\nname\nis\n" \points to second \n
lines[2]=0x0082fb0f"\nis\n" \points to third \n
lines[3]=0x0082fb12"\n" \points to last \n
这是有道理的,因为 object
中有 4 个 \n
。
现在我在下一行输入 xyzabc
,所以控制台看起来像:
hello
name
is
xyzabc
在 while 循环中,一切正常,直到行
object=object+temp;
一执行object=object+temp;
,调试器就显示:
object="\nhello\nname\nis\nxyzabc" \object does not end with \n because object = object + "\n" has not been executed yet
lines[0]=0x0082fb04 "pù\x4\x1lo\nname\nis"
lines[1]=0x0082fb0a "\nname\nis"
lines[2]=0x0082fb1f "\nis"
lines[3]=0x0082fb12""
object
的值符合预期,但 lines
中的指针指向的内容已被 object=object+temp
行修改
执行该行后的预期值为:
object="\nhello\nname\nis\nxyzabc"
lines[0]=0x0082fb04"\nhello\nname\nis\nxyzabc"
lines[1]=0x0082fb0a"\nname\nis\nxyzabc"
lines[2]=0x0082fb0f"\nis\nxyzabc"
lines[3]=0x0082fb12"\nxyzabc"
为什么会这样?以及如何附加 I object
和 temp
而不会遇到这个问题?
object + temp;
和 object + "\n";
都很好并且做正确的事情:连接字符串。但是,这是不正确的:
lines.push_back(object.c_str() + object_size + temp.size());
因为 (cppreference::string::c_str)...
Returns a pointer to a null-terminated character array with data equivalent to those stored in the string.
The pointer is such that the range [c_str(); c_str() + size()] is valid and the values in it correspond to the values stored in the string with an additional null character after the last position.
The pointer obtained from c_str() may be invalidated by:
- Passing a non-const reference to the string to any standard library function, or
- Calling non-const member functions on the string, excluding operator[], at(), front(), back(), begin(), rbegin(), end() and rend().
从 c_str
返回的指针不应该独立于字符串存储。如果你想在向量中存储字符串(而不是无效的指针)你应该使用 std::vector<std::string>
.
object
可能会在您将内容连接到其中时重新分配。这意味着指向其在 lines
中的内容的指针无效。那是未定义的行为。