Visual Studio 2010 及更早版本附带的 std::vector
的实现具有众所周知的特殊性:resize
方法具有以下签名(C++ 03 兼容):
void resize(size_type new_size, value_type value);
代替大多数其他 STL 实现(如 gcc 的 STL 或 STLport)早在 C++11 之前就使用的符合 C++11 的签名:
void resize(size_type new_size, const value_type& value);
第一个变体的问题是,在某些情况下,如果 value_type
具有对齐规范,它将无法编译:
struct __declspec(align(64)) S { ... };
std::vector<S> v; // error C2719: '_Val': formal parameter with __declspec(align('64')) won't be aligned
这是一个 well known除了使用 std::vector
的不同实现之外没有令人满意的解决方法的问题。
我正在寻找具有 MIT 风格许可的 std::vector
的编写良好、测试良好、自包含且与 STL 兼容的实现我可以将其作为对齐类型的首选容器放入我的项目中。
我考虑过从 STLport 或 gcc 的 STL 中提取它,但是,由于完全符合标准,它们都很大并且有许多重要的依赖关系。
(我非常乐意实现一个合理的 std::vector
子集,它只支持 push_back
,clear
, capacity
、size
、reserve
、resize
、swap
和数组索引。)
有什么想法吗?
最佳答案
Eigen 背后的人图书馆似乎找到了一个很好的解决方法,可以解决将“过度对齐的类型”(as Stephan T. Lavavej call them)存储到 std::vector
中的问题,如在 Visual Studio 的 STL 中实现的那样。
它们的实现似乎不必要的复杂(检查来源 here 和 here)但主要思想是用一个薄包装器封装进入 std::vector
的类型:
#include <vector>
template <typename T>
struct wrapper : public T
{
wrapper() {}
wrapper(const T& rhs) : T(rhs) {}
};
struct __declspec(align(64)) S
{
float x, y, z, w;
};
int main()
{
std::vector< wrapper<S> > v; // OK, no C2719 error
return 0;
}
关于Eigen中的实现,我必须承认我不太明白
- 为什么他们需要
Eigen::aligned_allocator_indirection
, - 为什么他们需要为
EIGEN_WORKAROUND_MSVC_STL_SUPPORT
中的算术类型设置异常(exception), - 为什么他们需要在
Eigen::workaround_msvc_STL_support
中定义所有这些构造函数和运算符, - 或者为什么他们需要在
std::vector
的部分特化中为Eigen::aligned_allocator_indirection
分配器重新定义resize
...
欢迎提供线索。关键是,这个技巧非常有效(据我所知),而且我没有发现它有任何问题,除了有点不雅。
关于c++ - std::vector 的自包含、STL 兼容实现,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/9409591/