包含换行符分隔的单词的文件和C++中这些单词的字符串向量的大小是否相同?

Do a file containing words separated by newline and a vector of strings for those words in C++ have same size?

本文关键字:单词 向量 是否 字符串 文件 分隔 换行符 C++ 包含      更新时间:2023-10-16

该文件的形式如下:

字1
字2 字3

...

我在从文件中读取这些单词后创建了字符串向量,如下所示:

std::vector<string> words;
string w;
ifstream file("input");
while(getline(file,w))
words.push_back(w);
file.close();

矢量占用的物理内存大小是否与输入文件的大小相同?为什么?

向量占用的物理内存大小是否与输入文件的大小相同?

这取决于"向量占用的物理内存大小">是什么意思。矢量对象本身的大小通常为 3 个指针(或 1 个指针和 2 个数字(,例如 64 位体系结构上的 24 个字节。但是,矢量随后会为至少N 个字符串对象动态分配空间,其中N文件行数。请注意,如果不保留向量空间,则可能会分配比N个字符串更多的空间。

每个字符串对象都有一些"内部"大小(在我的实验中,libc++/Clang 为 24 字节,libstdc++/GCC 为 32 字节(。

然后,每个字符串都需要存储文本行。它可能会动态分配内存,或者对于短字符串,它可能采用小字符串优化。对于动态内存分配,您需要考虑一些填充,因为动态分配的缓冲区是对齐的(在我的环境中为 16 字节(。

因此,您无法在此处轻松比较内存占用。但是,一般来说,字符串向量会有很多开销。


如果要避免这种开销,只需将整个文件内容读取到单个字符数组(矢量、字符串(中,然后创建一个附加数组,其中包含指向各个行开始位置的指针。

向量实现有两个内存占用空间:sizeof(vector)是堆栈上使用的内存(通常为 24 字节(,然后是动态分配的内存,首先是vector,其次是string参数。

向量分配的内存可能比容纳所有字符串的实际需要的内存多:如果按push_back(或emplace_back(增长它,每当容量不足时,它就会将动态分配的内存加倍。

最后,字符串有自己的开销:对于短单词(短于sizeof(string)(,字符串中未使用的内存被浪费,而对于长单词,字符串必须分配动态内存并保留单独的指针(导致内存开销(。

因此,答案是:NOvector<string>占用更多空间(可以分布在堆栈和堆上的不同位置之间(。