我有一些std::vector<unsigned int> v
包含一些内容(出于效果目的,我无法使用std::set
。
我想创建v
的否定版本,即包含所有剩余索引的向量。如果在[0,10]
,v=[0,2,4,6,8]
范围内,我想要否定版本nv=[1,3,5,7,9]
。
注意:v
已排序!
最有效的方法是什么?
答案 0 :(得分:1)
这是线性时间。
std::vector<unsigned int> getnv(unsigned rangebeg, unsigned rangeend, const std::vector<unsigned int>& v)
{
std::vector<unsigned int> nv;
nv.reserve(rangeend - rangebeg - v.size());
std::vector<unsigned int>::const_iterator next = v.begin();
// skip out-of-range values in v
while (next != v.end() && *next < rangebeg) {
++next;
}
for (unsigned i = rangebeg; i < rangeend; ++i)
{
if (next != v.end() && *next == i) {
++next;
continue;
}
nv.push_back(i);
}
return nv;
}
答案 1 :(得分:1)
似乎数组v[a,b,c......]
已经排序
然后,初始化vn=[]
并遍历元素并从v[i-1] to v[i] into vn[]
插入nos。
代码:
void insert_nos(int A, int B)
{
for(int i=A+1;i<B;i++)
vn.push_back(i);
}
insert_nos(range_start-1, v[0]);
for(int i=0;i<v.size()-1;i++)
insert_nos(v[i],v[i+1]);
insert_nos(v[v.size()-1],range_end+1);
确保处理边界情况。
复杂性: O(n)
答案 2 :(得分:1)
这是一个没有原始循环的版本:
std::array<int, 2> range{0,10};
std::vector<int> items{0, 1, 2, 4, 5, 9};
std::vector<int> v(range.back() - range.front() - items.size());
std::generate(v.begin(), v.end(),
[iter = items.cbegin(), endIter = items.cend(), i = range.front()] () mutable
{ while(iter < endIter && i == *iter) { ++iter; ++i; } return i++; });