std::vector::emplace_back比std::vector::push_back慢的例子
Examples where std::vector::emplace_back is slower than std::vector::push_back?
我最近在读Scott Meyer的《Effective Modern c++》。在第42项中,他声称,例如,std::vector::emplace_back
通常(但并不总是)与push_back
一样快,甚至更快。他列出了至少应该达到同样速度的三个条件,但没有提供在这些条件不全部满足的情况下的反例。有人能给我提供一个例子,使用emplace_back
会导致比使用push_back
更差的性能吗?
这取决于你所说的" emplace_back
比push_back
慢"是什么意思。考虑构造成本高而复制成本低的类,例如具有写时复制行为的类,或表示哈希值的类:
class Hash {
public:
int value;
Hash(const char *data) : value(very_expensive_hash_function(data)) {} // expensive
Hash(const Hash &other) : value(other.value) {} // cheap
};
Hash h(foo);
std::vector<Hash> v;
v.push_back(h); // 1
v.emplace_back("foo"); // 2
那么,(1)确实会比(2)快。然而,这种比较是不公平的。在比较性能时,应将所涉及的构造函数的成本考虑在内。
愚蠢的例子:
std::vector<always_throws_on_construction> vec;
if(vec.size() == vec.capacity())
{
vec.push_back(always_throws_on_construction());
}
可能比
快std::vector<always_throws_on_construction> vec;
if(vec.size() == vec.capacity())
{
vec.emplace_back();
}
本质上这归结为std实现。理论上,emplace应该总是一样快或更快,但现实是没有标准库实现充分利用了这一点。
几年前他就这个问题做过一次演讲:https://www.youtube.com/watch?t=3427&v=smqT9Io_bKo
查看前1个小时的演讲以获得更详细的解释。讲座最后的问答也是相关的。
相关文章:
- 使用std::multimap迭代器创建std::list
- C++中std::resize(n)和std::shrink_to_fit之间的区别
- 来自 std::list 的迭代器 .end() 按预期返回"0xcdcdcdcdcdcdcdcd"但 .begin()
- C++17复制构造函数,在std::unordereded_map上进行深度复制
- 如何导出包含具有"std::unique_ptr"值的"std::map"属性的
- 从持续时间构造std::chrono::system_clock::time_point
- std::具有相同基类的类的变体
- std::向量与传递值的动态数组
- 使用std::vector的OpenCL矩阵乘法
- 推导 std::vector::back() 的返回类型
- std::vector using back(), pop_back(), push_back(), 得到'double free or corruption'错误
- 在非空 std::list 上使用 std::list.back<int>() 时"Segmentation Fault"
- 为什么 std::string 的 back() 应该返回对字符的引用?
- 在std::vector中实现back()
- std::vector back()的奇怪行为
- std::vector::back 和 vector::operator[ vector::size() - 1] 之间
- 无法将 std::list 迭代器与 list::back()进行比较?
- 为什么对std::vector::back()的调用会使我的程序崩溃
- 为什么std::array::front和std::array::back不是noexcept
- std::string::back()