为什么fill_n()不能用于vector.reserve()?

时间:2016-01-22 11:10:14

标签: c++ c++11 vector stl-algorithm

我最近正在学习标准库算法,并对函数fill_n(iter, n, val)有疑问。此函数要求容器至少有n元素从iter开始。

以下是测试代码:

// Version 1, Error
vector<int> vec;
vec.reserve(10);  // Only allocate space for at least 10 elements
fill_n(vec.begin(), 10, 0);

// Version 2, OK
vector<int> vec;
vec.resize(10);  // Value initialized 10 elements
fill_n(vec.begin(), 10, 0);

// Version 3, OK
vector<int> vec;
fill_n(back_inserter(vec), 10, 0);  // Push back 10 elements via back_inserter

为什么版本1代码在版本2和版本2时出错? 3不是吗?

3 个答案:

答案 0 :(得分:4)

$('#contact-form').validate({ rules: { your_input_name: { required: true } }, messages: { your_input_name: { required: 'Field is required' } }, submitHandler: function() { var form = $(this); var post_data = form.serialize(); //Serialized the form data for process.php $('#loader').html('<img src="../spinner.gif" /> Please Wait...'); form.fadeOut(500, function() { form.html("<h3>Thank you.").fadeIn(); $('#loader').html(''); }); // Normally would use this $.ajax({ type: 'POST', url: 'process.php', // Your form script data: post_data, success: function(msg) { form.fadeOut(500, function() { form.html(msg).fadeIn(); }); } }); return false; } });仅保留空间,但向量的大小保持不变。由reserve返回的迭代器不能递增超过向量的末尾,并且因为它是确定向量结束位置的(未更改的)大小,所以会出现错误。

答案 1 :(得分:3)

版本1不起作用,因为:

std::reserve修改了向量的容量,而不是它的大小。 std::fill_n要求容器事先具有正确的尺寸

版本2有效,因为:

std::resize 修改向量的大小,而不仅仅是其容量。

版本3有效,因为:

std::back_inserter会在向量上调用push_back,该向量会添加到向量并相应地修改它的大小。

答案 2 :(得分:2)

reserve没有初始化任何内容。它只是保留一些空间,因此每次推送新项目时都不会重新分配。 因此,告诉fill_n将结果直接推送到最后的vector的解决方案。

改变这个:

// Version 1, Error
vector<int> vec;
vec.reserve(10);  // Only allocate space for at least 10 elements
fill_n(vec.begin(), 10, 0);

要:

// Version 1, Corrected
vector<int> vec;
vec.reserve(10);  // Only allocate space for at least 10 elements
fill_n(std::back_inserter(vec), 10, 0);