为什么libc ++的std :: string的实现占用了3x内存作为libstdc ++? [英] Why does libc++'s implementation of std::string take up 3x memory as libstdc++?
问题描述
请考虑以下测试程序:
#include< iostream>
#include< string>
#include< vector>
int main()
{
std :: cout< sizeof(std :: string(hi))<< ;
std :: string a [10];
std :: cout<< sizeof(a)< ;
std :: vector< std :: string> v(10);
std :: cout<< sizeof(v)+ sizeof(std :: string)* v.capacity()< \\\
;
}
输出 libstdc ++
和 libc ++
分别是:
8 80 104
240 264
如您所见, libc ++
需要3倍的内存为一个简单的程序。如何实现不同导致这种内存差异?
这是一个简短的程序,可以帮助您探索两种类型内存使用 std :: string
:堆栈和堆。
include< string>
#include< new>
#include< cstdio>
#include< cstdlib>
std :: size_t allocated = 0;
void * operator new(size_t sz)
{
void * p = std :: malloc(sz);
assigned + = sz;
return p;
}
void operator delete(void * p)noexcept
{
return std :: free(p);
}
int
main()
{
allocated = 0;
std :: string s(hi);
std :: printf(stack space =%zu,heap space =%zu,capacity =%zu \\\
,
sizeof(s),allocated,s.capacity());
}
使用 http://melpon.org/wandbox/ 很容易获得不同编译器/ lib组合的输出,例如:
gcc 4.9.1:
堆栈空间= 8,堆空间= 27,容量= 2
gcc 5.0.0 :
stack space = 32,heap space = 0,capacity = 15
clang / libc ++:
堆栈空间= 24,堆空间= 22
VS-2015:
堆栈空间= 32,堆空间= 0,capacity = 15
(最后一行来自 http://webcompiler.cloudapp.net )
上面的输出还显示了
capacity
,这是一个衡量多少char
该字符串可以保存之前,必须从堆中分配一个新的,更大的缓冲区。对于gcc-5.0,libc ++和VS-2015实现,这是对短字符串缓冲区的度量。也就是说,堆栈上分配的大小缓冲区保存短字符串,从而避免更昂贵的堆分配。
看来libc ++实现具有最小)的短字符串实现,并且还包含最大的短字符串缓冲区。如果你计算 total 的内存使用量(stack + heap),libc ++在这4个字符串中的总内存使用量最小。
应该注意,所有这些测量都是在64位平台上进行的。在32位上,libc ++栈的使用率将下降到12,小字符串缓冲区下降到10.我不知道其他实现在32位平台上的行为,但是你可以使用上面的代码来找出。
Consider the following test program:
#include <iostream> #include <string> #include <vector> int main() { std::cout << sizeof(std::string("hi")) << " "; std::string a[10]; std::cout << sizeof(a) << " "; std::vector<std::string> v(10); std::cout << sizeof(v) + sizeof(std::string) * v.capacity() << "\n"; }
Output for
libstdc++
andlibc++
respectively are:8 80 104 24 240 264
As you can see,
libc++
takes 3 times as much memory for a simple program. How does the implementation differ that causes this memory disparity? Do I need to be concerned and how do I workaround it?解决方案Here is a short program to help you explore both kinds of memory usage of
std::string
: stack and heap.#include <string> #include <new> #include <cstdio> #include <cstdlib> std::size_t allocated = 0; void* operator new (size_t sz) { void* p = std::malloc(sz); allocated += sz; return p; } void operator delete(void* p) noexcept { return std::free(p); } int main() { allocated = 0; std::string s("hi"); std::printf("stack space = %zu, heap space = %zu, capacity = %zu\n", sizeof(s), allocated, s.capacity()); }
Using http://melpon.org/wandbox/ it is easy to get output for different compiler/lib combinations, for example:
gcc 4.9.1:
stack space = 8, heap space = 27, capacity = 2
gcc 5.0.0:
stack space = 32, heap space = 0, capacity = 15
clang/libc++:
stack space = 24, heap space = 0, capacity = 22
VS-2015:
stack space = 32, heap space = 0, capacity = 15
(the last line is from http://webcompiler.cloudapp.net)
The above output also shows
capacity
, which is a measure of how manychar
s the string can hold before it has to allocate a new, larger buffer from the heap. For the gcc-5.0, libc++, and VS-2015 implementations, this is a measure of the short string buffer. That is, the size buffer allocated on the stack to hold short strings, thus avoiding the more expensive heap allocation.It appears that the libc++ implementation has the smallest (stack usage) of the short-string implementations, and yet contains the largest of the short string buffers. And if you count total memory usage (stack + heap), libc++ has the smallest total memory usage for this 2-character string among all 4 of these implementations.
It should be noted that all of these measurements were taken on 64 bit platforms. On 32 bit, the libc++ stack usage will go down to 12, and the small string buffer goes down to 10. I don't know the behavior of the other implementations on 32 bit platforms, but you can use the above code to find out.
这篇关于为什么libc ++的std :: string的实现占用了3x内存作为libstdc ++?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!