我在Eigen3库中有一些复杂,密集的矢量/矩阵,我想将实部和虚部提取到单独的数组中.在Matlab中,我可以做类似的事情
cplxFoo = [1, 1i; -1i -1]
re = real(cplxFoo)
im = imag(cplxFoo)
Run Code Online (Sandbox Code Playgroud)
期望收益率
cplxFoo =
1.0000 + 0.0000i 0.0000 + 1.0000i
0.0000 - 1.0000i -1.0000 + 0.0000i
re =
1 0
0 -1
im =
0 1
-1 0
Run Code Online (Sandbox Code Playgroud)
有喜欢什么real(),并imag()在Eigen3 Matlab的功能呢?
现在,我所知道的唯一可行的东西就是类似的东西
MatrixXcd cplxFoo = ...;
MatrixXd re(cplxFoo.rows(), cplxFoo.cols());
MatrixXd im(cplxFoo.rows(), cplxFoo.cols());
for(size_t j=0; j<cplxFoo.cols(); ++j) {
for(size_t i=0; i<cplxFoo.rows(); ++i) {
re(i, j) = cplxFoo(i,j).real();
im(i, j) = cplxFoo(i,j).imag();
}
}
Run Code Online (Sandbox Code Playgroud)
它工作,我甚至可以把它放在一个函数中,但后来我不得不做我自己的循环矢量化,展开等,而且我必须做一个额外的副本. …
自2016年11月起,可以编译引用Eigen3.3的CUDA代码 - 请参阅此答案
这个答案不是我正在寻找的,现在可能已经"过时",因为现在可能有一种更简单的方法,因为以下是在文档中写的
从Eigen 3.3开始,现在可以在CUDA内核中使用Eigen的对象和算法.但是,仅支持一部分功能,以确保在CUDA内核中不会触发动态分配.
另见这里.不幸的是,我无法找到任何这样的例子.
现在是否可以编写如下的内核,它应该只计算一堆点积?
__global__ void cu_dot(Eigen::Vector3d *v1, Eigen::Vector3d *v2, double *out, size_t N)
{
int idx = blockIdx.x * blockDim.x + threadIdx.x;
if(idx < N)
{
out[idx] = v1[idx].dot(v2[idx]);
}
return;
}
Run Code Online (Sandbox Code Playgroud)
我可以编译它,但它似乎不起作用.当我尝试将数据复制到主机时,我明白了illegal memory access.请注意,我最初将Vector3d存储为`std :: vector然后分别使用
cudaMalloc((void **)&p_device_v1, sizeof(Eigen::Vector3d)*n);
cudaMemcpy(p_v1_device, v1.data(), sizeof(Eigen::Vector3d)*n, cudaMemcpyHostToDevice);
Run Code Online (Sandbox Code Playgroud)
我在https://github.com/GPMueller/eigen-cuda上使用CMake 建立了一个MWE项目
我实现了一个比较操作operator<的Eigen::VectorXd,有时候,我需要通过一个比较功能,以我的另外一个功能,我累了包裹的operator<到[](const VectorXd& v1, const VectorXd& v2)->bool{return v1 < v2},所以我认为std::less类是有用的,因为,我的理解,它可以生成lambda函数只要operator<定义.
但是,我发现这std::less<VectorXd>对我不起作用,例如,下面的代码工作正常:
#include "Eigen/Dense"
#include <iostream>
#include <functional>
using namespace std;
using namespace Eigen;
struct T
{
int x;
};
bool operator<(const T& t1, const T& t2)
{
return t1.x < t2.x;
}
bool operator<(const VectorXd& v1, const VectorXd& v2)
{
return (v1.array() <= v2.array()).all() and (v1 != v2);
}
int main()
{
T t1, t2;
t1.x = …Run Code Online (Sandbox Code Playgroud) 我想知道是否可以在编译时自动构造/初始化static const Eigen::Matrix ?我想这强制需要所有 Eigen::Matrix 类型的constexpr CTOR 等。但是,我在 Eigen3 doxy 中发现没有有关任何constexpr方法的信息。
有人可以引用或回答这些陈述/问题吗?
我正在将2D Eigen::Array用于项目,我喜欢在大型2D阵列的情况下继续使用它们.
为了避免内存问题,我想使用内存映射文件来管理(读取/修改/写入)这些数组,但我找不到工作示例.
我发现最近的例子是此基础上boost::interprocess,但它使用的共享内存(而我更愿意有持久存储).
缺乏示例让我担心是否有更好的主流替代解决方案来解决我的问题.是这样的吗?一个最小的例子非常方便.
编辑:
这是在评论中解释我的用例的最小示例:
#include <Eigen/Dense>
int main()
{
// Order of magnitude of the required arrays
Eigen::Index rows = 50000;
Eigen::Index cols = 40000;
{
// Array creation (this is where the memory mapped file should be created)
Eigen::ArrayXXf arr1 = Eigen::ArrayXXf::Zero( rows, cols );
// Some operations on the array
for(Eigen::Index i = 0; i < rows; ++i)
{
for(Eigen::Index j = 0; j < cols; ++j)
{
arr1( i, …Run Code Online (Sandbox Code Playgroud) 请考虑以下代码.
const int N = 100;
const float alpha = 0.9;
Eigen::MatrixXf myVec = Eigen::MatrixXf::Random(N,1);
Eigen::MatrixXf symmetricMatrix(N, N);
for(int i=0; i<N; i++)
for(int j=0; j<=i; j++)
symmetricMatrix(i,j) = symmetricMatrix(j,i) = i+j;
symmetricMatrix *= alpha;
symmetricMatrix += ((1-alpha)*myVec*myVec.adjoint());
Run Code Online (Sandbox Code Playgroud)
它基本上实现了指数平均.我知道最后一行可以通过以下方式进行优化.
symmetricMatrix_copy.selfadjointView<Eigen::Upper>().rankUpdate(myVec, 1-alpha);
Run Code Online (Sandbox Code Playgroud)
我想知道我是否能以有效的方式结合最后两行.总之,我想计算 A = alpha*A+(1-alpha)*(x*x').
我编写了一个函数,将10x10维的本征矩阵相乘。然后,我编写了一个朴素的乘法函数CustomMultiply,它比Eigen的实现快2倍。
我尝试了几个不同的编译标志,例如-O2和-O3,它们没有什么不同。
#include <Eigen/Core>
constexpr int dimension = 10;
using Matrix = Eigen::Matrix<double, dimension, dimension>;
Matrix CustomMultiply(const Matrix& a, const Matrix& b) {
Matrix result = Matrix::Zero();
for (int bcol_idx = 0; bcol_idx < dimension; ++bcol_idx) {
for (int brow_idx = 0; brow_idx < dimension; ++brow_idx) {
result.col(bcol_idx).noalias() += a.col(brow_idx) * b(brow_idx, bcol_idx);
}
}
return result;
}
Matrix PairwiseMultiplyEachMatrixNoAlias(int num_repetitions, const std::vector<Matrix>& input) {
Matrix acc = Matrix::Zero();
for (int i = 0; i < num_repetitions; ++i) …Run Code Online (Sandbox Code Playgroud) 我正在尝试包装一个 C++ 函数,该函数接受 Eigen::Quaternion 作为 python 使用的参数。该函数定义如下:
void func(const Eigen::Quaternion<double> &rotation) {...}
Run Code Online (Sandbox Code Playgroud)
我正在使用 pybind11 将其包装为 python,在我的 pybind11 中我有:
#include <pybind11/eigen.h> // I have this included
PYBIND11_MODULE(example, m)
{
m.def("func", &func, "example function");
}
Run Code Online (Sandbox Code Playgroud)
一切看起来都不错,它可以编译,但是当我通过以下方式调用它时:
func(np.array([0, 0, 0, 1]))
Run Code Online (Sandbox Code Playgroud)
我收到错误:
func():函数参数不兼容。支持以下参数类型: 1. (arg0: Eigen::Quaternion<double,0>) -> None
是否进行了一些谷歌搜索,但找不到关于 Eigen::Quaternion 是否可以转换为 numpy 数组/从 numpy 数组转换以及应该使用什么形状的数组的答案?我认为四元数可以从 4 元素 numpy ndarray 转换而来,但似乎不是,有人知道如何做到这一点吗?
我正在尝试使用 OpenMP 缩减来并行化以下循环;
#define EIGEN_DONT_PARALLELIZE
#include <iostream>
#include <cmath>
#include <string>
#include <eigen3/Eigen/Dense>
#include <eigen3/Eigen/Eigenvalues>
#include <omp.h>
using namespace Eigen;
using namespace std;
VectorXd integrand(double E)
{
VectorXd answer(500000);
double f = 5.*E + 32.*E*E*E*E;
for (int j = 0; j !=50; j++)
answer[j] =j*f;
return answer;
}
int main()
{
omp_set_num_threads(4);
double start = 0.;
double end = 1.;
int n = 100;
double h = (end - start)/(2.*n);
VectorXd result(500000);
result.fill(0.);
double E = start;
result = integrand(E); …Run Code Online (Sandbox Code Playgroud) 我已经用 Eigen 实现了一段代码,我希望 Eigen 使用 BLAS 和 LAPACK 。
我在这里看到,这是可能的,但我不知道如何或将这些值/指令放在代码中的位置。
我必须在某个地方指定价值,EIGEN_USE_BLAS但我不知道在哪里。
我已经看到 Eigen 的源代码包括 BLAS 和 LAPACK 的代码,但我完全忽略它是否默认使用它或什么。我正在使用 Eigen 3.3.3。