我有一个下面的代码片段。我期望输出为string contents = File.ReadAllText(@"C:\SQLFiles\MySQLFile.sql");
,但奇怪的是它会输出垃圾字符。
mystring
(1)
我最初的想法是#include <iostream>
#include <string>
using namespace std;
int main(int argc, char *argv[]) {
string s1("mystring");
const char* s2 = s1.c_str();
s1 = "Hi there, this is a changed string s1";
cout << s2 << endl;
return 0;
}
会分配足够的内存
保持c_str
并返回分配给s1
的那个内存块的地址,然后s2
和s1
从这里开始独立地运行。
(2)
但是当我分配s2
时,我在(1)中的想法被证明是错误的。 s1 = "Hi there ..... "
仍在某种程度上影响着s1
。
(3)
当我在s2
行中注释掉时,一切正常,即s1 = "Hi there .... "
得到一致的打印。
(4)
对于(1)中的说法,我并没有真正说服mystring
正在分配内存以容纳c_str
,因为如果是这种情况,我们将不得不通过s1
处理释放该内存块我们不做的指针。所以我不确定。
请帮我解释这种奇怪的行为。
答案 0 :(得分:11)
引用cppreference:
从
c_str()
获得的指针可能因以下原因而失效:
- 在字符串上调用非常量成员函数,但不包括operator [],at(),front(),back(),begin(),rbegin(),end()和 rend()。
通过修改字符串,您将不再具有有效的指针。
此外,您的前提是错误的。没有分配/释放内存c_str
。 c_str
和data
(在C ++ 11中相同)返回指向基础存储的指针。它不拥有该存储。无论出于何种原因更改了存储,指针都将不再有效(即,它现在可能指向垃圾)。
答案 1 :(得分:6)
s1.c_str()
不返回独立于s1
的内存。更改为s1
返回的指针s1.c_str()
无效。
换句话说,请小心使用c_str
。通常,使用它可以将C字符串传递给不接受C ++字符串的函数。