【发布时间】:2013-10-09 20:34:13
【问题描述】:
我正在使用 gcc 4.8.1,经过数小时调试一个可怕的神秘性能问题后,我发现 std::list::size 实际上是作为对 std::distance 的调用实现的。
/** Returns the number of elements in the %list. */
size_type
size() const _GLIBCXX_NOEXCEPT
{ return std::distance(begin(), end()); }
这让我很惊讶,因为参考资料说complexity of std::list::size should be constant 和std::distance 的复杂性对于std::list::iterator 是线性的。
我真的很困惑,因为我认为 gcc 对 C++11 特性有很好的支持,我看不出他们为什么不实现这个。
这是引用中的错误还是 gcc 中的错误?
在后一种情况下:
有什么理由让这样一个基本的 C++11 特性消失了这么久?
是否有第三种可能性,例如:
我可以有 gcc 4.8.1 但标准库的一些旧版本吗?
【问题讨论】:
-
在 C++03 中是
O(n),在 C++11 中已经更改,现在是O(1)。似乎 GCC 还没有更新这个位。不好。 -
GCC 有许多违反 C++11 的标准。
list和string浮现在脑海中;在遵守旧代码和破坏旧代码之间做出艰难的选择。 -
@MartinDrozdik:在算法上似乎存在问题。通常你需要
empty(),但很少需要size()。如果您的算法确实需要一个列表(而不是向量),您通常只需查询列表中是否有 something 并将其弹出。 -
@MartinDrozdik:
vector在使用push_back时具有摊销复杂性,因此您应该能够让它以相对较低的成本增长(取决于在其中移动对象的成本,当然)。 -
gcc-5 默认情况下具有 C++11 兼容
std::list和std::string。这是其他人指出的 ABI 重大更改。有一种机制涉及允许切换的内联命名空间。努力确保旧的库不会损坏。我相信这将在发布时更详细地说明,应该是 RSN。
标签: c++ gcc c++11 c++-standard-library