我想创建一组数字:0,1,2,3,4 ...... 以下代码无法编译:
std::set<int> s;
std::iota(s.begin(), s.end(), 0);
出现以下错误消息:
error C3892: '_First' : you cannot assign to a variable that is const
编译器是VC ++ 2012。相同的代码适用于矢量。我应该如何使用它?
更新
我现在可以看到我的代码没有意义,因为没有指定设置大小。
以下是有关我的问题的更多详细信息。
我有一个包含[0,N]范围内某些数字的集合。在我的应用程序中,我需要多次计算这些集合的集合差异。 N是固定的。
我们说N = 5
,第一组是s1 = {0, 3, 4}
。我需要计算集合差异{0, 1, 2, 3, 4} \ {0, 3, 4} == {1, 2}
。对于不同的集合,应该经常执行此操作,因此我认为我可以创建一个包含所有数字的集合(在这种情况下为{0, 1, 2, 3, 4}
)并使用std::set_difference
来计算这些差异。
答案 0 :(得分:12)
要解决您的实际问题,std::set_difference
与std::set
的关联程度低于您的预期。您可以使用任意一对迭代器作为set_difference
的前两个参数,前提是它们按顺序返回值。作为一套,没有特别的好处。
因此,例如,包含值0 ... n-1的std::vector
的开始/结束迭代器将按顺序工作,或者是一对boost::counting_iterator
:
std::set result;
std::set_difference(
boost::counting_iterator<int>(0), boost::counting_iterator<int>(n),
s1.begin(), s1.end(),
std::inserter(result, result.end())
);
输出也不需要设置,您也可以vector
使用back_inserter
。
要解决您的问题:尝试在集合上使用iota
没有意义。 iota
通过为其指定新值来更改范围中包含的值。您无法分配set
。
如果您想要一个包含数字0 ... n-1
的集合,那么:
std::set<int> s;
for (int i = 0; i < n; ++i) {
s.insert(s.end(), i);
}
如果有人告诉你循环是为了wusses而真正的C ++程序员使用算法,那么如果你真的想要你可以参与iota
:
std::set<int> s;
{
std::vector<int> vec(n);
std::iota(vec.begin(), vec.end(), 0);
s.insert(vec.begin(), vec.end());
}
不幸的是,这种效率低下。因此,如果您非常喜欢算法,以至于您可以将它们结合起来,那么您可以到达标准库之外:
std::set<int> s(boost::counting_iterator<int>(0), boost::counting_iterator<int>(n));
答案 1 :(得分:2)
略显不雅的选择:
set<int> s;
generate_n(inserter(s, s.end()), 10, [&]{ return s.size(); });
答案 2 :(得分:1)
集合与向量的不同之处在于向量具有从索引到存储在该索引处的值的关联,而集合仅具有值是否在集合中的信息。因此,为set元素赋值是没有意义的 - 强制执行它的方法是集合中的元素是常量。
执行此操作的等效方法类似于删除集合中不需要的值(在向量的情况下为“旧”值),然后遍历要存储的值(使用itoa)它将是一个递增值的序列)并将它们逐个添加到集合中。