cppreference关于map::emplace_hint()
:
template <class... Args> iterator emplace_hint( const_iterator hint, Args&&... args );
使用
hint
作为元素应该去的建议,将新元素插入到容器中。
因此,如果这是一个建议,那是否意味着实现没有将元素放在那里?究竟是什么提示?
答案 0 :(得分:9)
cppreference对map::emplace_hint()
的准确性不准确。但是,应该可以原谅这一点,因为在C ++ 11之前的某个时刻,草案明确授予了实现忽略提示的权限:
来自N3225,表102:
...允许实现忽略提示。
幸运的是,这已由LWG 1253和C ++ 11及前向读取更正:
...元素尽可能靠近
p
之前的位置插入。一般情况下是对数,但如果在
之前插入元素,则摊销常数p
所以“提示”现在有了牙齿。 必须得到尊重。虽然请注意,这些注释仅适用于关联容器(map,multimap,set,multiset)。
在C ++ 98/03中,“提示”未正确用于insert
。但N1780更正了这一点,随后emplace_hint
采用了这一措辞。
继续允许实现忽略无序容器的提示。这是有充分理由的。没有良好的实施策略来利用无序容器的提示。提示只是为了提供与容器通用代码中的关联容器的兼容性。
答案 1 :(得分:8)
通常,插入基于树的映射(如std::map
)需要进行O(log n)查找才能找到正确的插入点。如果正确的插入点与您提供的提示相邻,则可以保存O(log n)查找,而操作为O(1)。
通常的用例是在没有给定密钥的现有项目时插入项目。然后,不是使用.find()
(如果找不到该项,则返回.end()
),而是使用.lower_bound()
来查找现有键(如果是,则返回插入点的迭代器)密钥未找到)。然后,如果密钥不存在,则使用该迭代器进行提示插入。
答案 2 :(得分:1)
std::map
是一个关联容器,用于保持键值对按键排序。由于与查找相关的成本,插入具有O(logN)复杂度。但是通过提供一个提示,迭代器从哪里开始搜索 - 插入可以在分摊的常量时间而不是对数时间内进行。