我在here这样的很多地方读过std::vector
总是连续的,但是我没有找到解释这个含义的原因,或者为什么这个很重要?
这是否意味着他们在记忆中有固定的位置或者什么?
答案 0 :(得分:7)
连续意味着顺序编号的矢量元素在存储空间中彼此相邻。例如,如果元素i
位于地址a
,且大小为s
,则元素i+1
将位于地址{{1} }},元素a+s
将位于i+2
,依此类推。
这有两个重要原因:
答案 1 :(得分:2)
std::vector
中的元素占用连续的内存块。 std::vector
是一个改进的数组。
这很重要,因为这意味着对任意元素的访问速度很快。由于元素的大小和数量是已知的,因此您可以快速查找任何元素。
缺点是任何重组,例如在中间插入或删除元素,都是一项昂贵的操作,因为它需要对所有其他重组进行洗牌以维持连续性。
其他数据结构(如列表)可以更轻松地进行其他权衡重组。
答案 2 :(得分:2)
这意味着你总是可以通过指针算法到达下一个元素的地址。
答案 3 :(得分:2)
这意味着std::vector
的内存表示中没有空洞。它在内存中看起来像这样:
每个方块代表内存中的一个地址,每个橙色代表一个元素占用的内容。
大多数其他容器不是连续的。例如,std::forward_list
在内存中看起来像这样:
此处,橙色地址再次包含容器的元素。但它们分散在记忆中。还有灰色元素;它们代表列表所需的额外内存,以便每个元素都知道下一个元素的位置。 [*]
可以想象,std::vector
清晰简洁的记忆表现形式给你带来了很多好处。它解释了为什么std::vector
有其他容器缺少的操作,或者为什么这些操作在恒定时间运行。例如,为了获得第n个元素,您只需执行一次加法(基址+ n)。它还解释了为什么你可以安全地使用&v[0]
并在其上执行指针算术。
[*]这有点简化,因为该示例具有char
个元素,但是在典型的C ++实现中,列表中的指针比单个char
占用更多内存。更现实的图表将为每个元素使用4或8个灰色方块,因为它是典型现代机器上一个指针的大小。
答案 4 :(得分:1)
由于没有一个答案提到它:
感谢private void CompareTreeViewItem(TreeViewItem TViewItem1,TreeViewItemTViewItem2)
{
if ((string)TViewItem1.Header == (string)TViewItem2.Header)
{
TViewItem2.IsExpanded = TViewItem1.IsExpanded;
if (TViewItem1.Items.Count > 0)
{
for (int i = 0; i < TViewItem1.Items.Count && i < TViewItem2.Items.Count; i++)
{
CompareTreeViewItem((TreeViewItem)TViewItem1.Items[i],
(TreeViewItem)TViewItem2.Items[i]);
}
}
}
}
的这一功能,您可以执行
std::vector
您可以避免逐个元素地读/写。
这可以在C ++ 03中使用,如(C ++ 03)标准(23.2.4.1)中所述
std::ifstream file( "file.txt", std::ios::ate | std::ios::binary ); std::vector<char> vec; if (!file) { file.seekg(0, std::ios_base::end); auto fileSize = file.tellg(); vec.resize(fileSize); file.seekg(0, std::ios_base::beg); // here we leverage contiguous memory in std::vector file.read(&vec[0], fileSize); }
的元素是连续存储的,这意味着vector
是{。}}v
其中vector
是T
以外的某种类型,然后它遵循。bool
所有&v[n] == &v[0] + n
的身份0 <= n < v.size()
。