C++中"机械臂"的机制是什么?
What's the mechanism of `inserter` in C++?
我尝试了代码吹气,inserter
和back_inserter
做了相同的lst3
,但我认为inserter
应该生成一个{4,3,2,1}
列表,因为新元素应该在lst3.begin()
之前插入到位置。为什么它们会产生相同的结果? 谢谢!
int main() {
list<int> lst = {1,2,3,4};
list<int> lst3;
// copy(lst.cbegin(), lst.cend(), inserter(lst3, lst3.begin()));
copy(lst.cbegin(), lst.cend(), back_inserter(lst3));
for_each(lst.cbegin(), lst.cend(), [] (const int i) {cout<<i<<endl;});
return 0;
}
元素应该插入到lst3.begin()之前的位置
你想象的等价物是这样的:
copy(lst.cbegin()+0, lst.cbegin()+1, inserter(lst3, lst3.begin()));
copy(lst.cbegin()+1, lst.cbegin()+2, inserter(lst3, lst3.begin()));
copy(lst.cbegin()+2, lst.cbegin()+3, inserter(lst3, lst3.begin()));
copy(lst.cbegin()+3, lst.cbegin()+4, inserter(lst3, lst3.begin()));
(假装这些+
操作将在列表迭代器上工作)
我明白你为什么会这么想,但没有。
当你向inserter
提供lst3.begin()
时,这个迭代器不会被存储/缓存和重复使用——我们知道它不可能,因为(考虑一下一般情况;列表特别不容易出现这种情况)这样的迭代器可能会被每个插入操作失效。
相反,迭代器在每次操作后递增。
CPP偏好对此进行了解释:
插入序列容器时,插入点会前进,因为每个 std::insert_iterator::operator= 都会更新目标迭代器
事实上,我们可以从 cpp首选项insert_iterator::operator=
页面中亲眼看到这一点。
最终结果是,您实际上是在以线性的、从左到右的顺序插入,例如:
copy(lst.cbegin()+0, lst.cbegin()+1, inserter(lst3, lst3.begin()));
copy(lst.cbegin()+1, lst.cbegin()+2, inserter(lst3, lst3.begin()+1));
copy(lst.cbegin()+2, lst.cbegin()+3, inserter(lst3, lst3.begin()+2));
copy(lst.cbegin()+3, lst.cbegin()+4, inserter(lst3, lst3.begin()+3));
(假装这些+
操作将适用于列表迭代器)
这种行为实际上更直观;整个源范围已按其原始顺序插入到lst3.begin()
开头的位置。
你看到的行为对于 std::inserter() 是正确的。
您期望的行为 - 即始终在前面插入 - 是您使用 std::front_inserter() 获得的行为。
@Lightness Races in Orbit的答案是正确的。
简而言之,std::inserter(container, iterator_argument)
始终绑定到最初传入的iterator_argument
位置。
例如:
vector<int> vec = {1,2,3,4};
auto it = std::inserter(vec, vec.begin() + 1);
内部状态:
1,2,3,4
↑
it
插入一个元素:
*it = 888;
内部状态:
1,888,2,3,4
↑
it
插入一个元素:
*it = 999;
内部状态:
1,888,999,2,3,4
↑
it
所以你不会得到一个相反的顺序序列。
顺便说一句,对于std::inserter
,您只需要继续执行插入*it = value
。it++
或++it
对std::inserter
没有影响.这个位置是永远绑定的。
另请查看文档:
https://en.cppreference.com/w/cpp/iterator/insert_iterator/operator=
1) 结果
iter = container->insert(iter, value); ++iter;
那么container->insert(iter, value);
的价值是什么?
它:
https://en.cppreference.com/w/cpp/container/vector/insert
1-2) 指向插入值的迭代器
std::inserter
函数从传递给函数的参数创建一个std::insert_iterator
对象。
您遇到的问题是由于两件事:
- 首先是复制迭代器
- 第二个是当容器为空时,其
begin
迭代器等于其end
迭代器。
因此,std::insert_iterator
对象将具有列表end
迭代器的副本,因此插入列表的末尾。
由于您从现有列表的开头进行迭代,并且始终在末尾插入,因此效果将与使用std::back_inserter
完全相同,其中元素按迭代顺序插入。
- 为不同配置设置MSVC_RUNTIME_LIBRARY的正确方法是什么
- C++避免重复声明的语法是什么
- 在C++中,将大的无符号浮点数四舍五入为整数的最佳方法是什么
- 实现无开销push_back的最佳方法是什么
- C++从另一个类访问公共静态向量的正确方法是什么
- "throw expression code" 1e7 >返回 d 是什么?投掷标准::overflow_error( "too big" ) : d;意味 着?
- C++中名称篡改的目的是什么
- 在 c++ 中拥有一组结构的正确方法是什么?
- 这个指针和内存代码打印是什么?我不知道是打印垃圾还是如何打印我需要的值
- 是什么阻止DOMTimerCoordinator::NextID进入无休止的循环
- 使用共享指针时,从共享指针本身释放内存的机制是什么
- C++20 中协程的机制是什么
- 使用C 17处理Unicode的有效,符合标准的机制是什么
- 带缓冲区的 iostream 的机制是什么?
- C++中"机械臂"的机制是什么?
- 与Java的InputMismatchException和IOException Handling等效的C++异常处理机制是什么
- QTimer对象是否在单独的线程中运行?它的机制是什么
- QNetworkAccessManager中的并行机制是什么
- 什么时候使用std::promise优于其他std::线程机制是一个好主意?
- 当我从赋值操作符返回值时,首先,调用复制构造函数的机制和基础是什么?