打破严格的混叠,并活着讲述它
Breaking strict aliasing and living to tell about it?
我试图在我用c++ 11编写的同一应用程序中使用两个库,LIBSVM和LIBLINEAR。LIBSVM和LIBLINEAR的输入本质上都是基于行的稀疏矩阵表示:有节点结构
struct svm_node
{
int index;
double value;
};
,稀疏矩阵本身就是struct svm_node **
,其中每一行都是struct svm_node *
,行以index = -1
结束。这个结构体的线性版本称为feature_node
,具有相同的定义。虽然LIBSVM和LIBLINEAR是由同一作者编写的,但svm.h
和linear.h
,因此struct svm_node
和struct feature_node
没有任何关系。
在某些情况下,我想为我的数据创建一个内核SVM模型(仅由LIBSVM实现)和一个逻辑回归模型(仅由LIBLINEAR实现)。数据集以各自的——在二进制级别上,相同的——稀疏矩阵表示传递给库,可能相当大,我宁愿避免对其进行memcpy()
处理。一个简单的reinterpret_cast<feature_node **>(svm_node_ptr_ptr_variable)
似乎可以很好地完成这项工作。
我也在发布版本中使用LLVM的全程序优化(-flto
),所以我想确保代码不会以不可预测的方式进行优化。
是否有任何方法将svm_node **
类型双关到feature_node **
,以避免可能由(当前或将来)编译器优化引起的任何损坏?__attribute__((__may_alias__))
在这里有帮助吗?如果有,我应该如何使用它?
如果__attribute__((__may_alias__))
只对类型有意义,如果我创建自己的结构体和指向结构体的指针,它会起作用吗
struct __attribute__((__may_alias__)) SparseElement {
int index;
double value;
};
typedef SparseRow SparseElement * __attribute__((__may_alias__));
然后将retinterpret_cast
ed SparseRow *
传递给LIBSVM和LIBLINEAR?
该结构体的线性版本称为feature_node,具有相同的定义。
如果你使用联合,你就是黄金。c++特别允许(第9.2节)访问"公共初始子序列"。
如果一个标准布局联合包含两个或多个共享公共初始序列的标准布局结构体,并且如果标准布局联合对象当前包含这些标准布局结构体中的一个,则允许检查其中任何一个的公共初始部分。如果对应的成员具有与布局兼容的类型,并且两个成员都不是位域或,则两个标准布局结构共享一个公共初始序列对于包含一个或多个初始成员的序列,它们都是具有相同宽度的位域。
即使是指针上的reinterpret_cast
也可以正常工作,因为经历左值到右值转换的类型正是存在于该内存中的对象的类型。
- "throw expression code" 1e7 >返回 d 是什么?投掷标准::overflow_error( "too big" ) : d;意味 着?
- NodeJs 服务器充斥着 UDP 广播,不发送响应
- 什么 /可以/ 你从一个函数返回. 并期望它在到达时还活着?
- 全局变量在 C++ 中是否显着提高了编译速度?
- 检查分离的线程是否还活着?
- C++:这两种将数字写入矩阵的方式之间是否存在显着的速度差异?
- std::future可以比std::promise活得更长吗
- 拿着锁时分叉
- 使 Windows 10 讲述人说出一些文本
- 在 OpenMP 中使用并行块时没有看到任何显着改进C++
- 活着的邻居细胞未正确计数
- 写一个活着的线程
- Lua 关机双免费,关机期间 Lua 线程还活着?
- Android NDK:保持活着的C 对象
- C++线程在kill之后仍然活着
- MFC还活着吗
- adobe ASL(亚当和夏娃)还活着吗?什么是替代品
- 打破严格的混叠,并活着讲述它
- 如何知道我的对象在c++中是否活着
- 有史以来活着的恐龙数量最多