堆栈上c ++字符和字符串的内存分配

时间:2014-09-15 12:35:04

标签: c++ string visual-c++ memory-leaks g++

考虑以下功能:

void Foo()
{
   std::string s = "Hello";
}

在上面的情况下,字符串是分配的吗?有些页面(如this)表示它在堆上,Microsoft表示它取决于大小。我怎样才能在堆上和堆栈上确定它(如果我想避免使用new())?

考虑另一个功能:

void Foo2()
{
   char *c = "Hello";
}

在这种情况下,我认为它是在堆栈上,但是一旦我通过MS Visual C ++检查它的程序集,我认为它在堆上。这是真的吗?

char c[] = "Hello"在哪里?

我正在使用VC12,但我想知道g ++也是如此。

由于异常处理,这对我很重要。因为在展开堆栈的情况下,如果在堆上创建数据并且在另一方面没有问题,我真的会丢失数据,但堆栈可能太大。

2 个答案:

答案 0 :(得分:0)

void Foo()
{
   std::string s = "Hello";
}

依赖于实施。
正如您所说,MSVC的标准库将为大型字符串分配堆,为较小的字符串分配本地存储(堆栈) 它的存储方式将根据您使用的标准库的平台/版本而有所不同。存储没有在C ++规范中定义,只是功能。

void Foo2()
{
   char *c = "Hello";
}

指针c在堆栈上,但实际数据是只读的,不在堆栈中或堆上。
它实际上存储在内存中的只读数据块中。

void Foo3()
{
   char c[] = "Hello";
}

数组c存储在堆栈中。初始化时,使用与Foo2()中相同的源中的字符串“Hello”创建它。但是,当c位于堆栈上时,*c指向可以修改的数据。

答案 1 :(得分:0)

std::string管理自己。 在代码中:

void foo() {
    std::string s = "Hello";
}

s是一个堆栈变量。字符串"Hello"的存储方式最多为std::string 你不需要担心它 - 除非你的特定STL实现是错误的,否则一切都会成功。

在:

void bar() {
    char* c = "Hello";
}

您已声明一个指向文字字符串"Hello"的本地指针。这取决于编译器的位置,但它可能在只读存储器段中。 值得注意的是,在这种情况下,字符串“Hello”是一个常量 - 在C ++ 98中,尝试修改它在技术上已被弃用(我相信C ++ 11中的完全错误)。

在:

void baz() {
    char c[] = "Hello";
}

整个字符串“Hello”;存储在本地6元素字符数组中(即在您的堆栈上)。

对于大多数情况,std::string的解决方案更受欢迎。

相关问题