在 Rcpp(Eigen) 中的 NumericVector/Matrix 和 VectorXd/MatrixXd 之间转换以执行 Cholesky 求解

Posted

技术标签:

【中文标题】在 Rcpp(Eigen) 中的 NumericVector/Matrix 和 VectorXd/MatrixXd 之间转换以执行 Cholesky 求解【英文标题】:Converting between NumericVector/Matrix and VectorXd/MatrixXd in Rcpp(Eigen) to perform Cholesky solve 【发布时间】:2013-12-06 23:42:01 【问题描述】:

编辑:从下面 Dirk 的回答中得到一些线索,我解决了这个问题,现在问题正文中的解决方案。

我确信这必须记录在某处,但我的谷歌技能让我失望。

我正在开发一个我认为不需要的 Rcpp 包 依赖于 Eigen,所以我非常广泛地使用了NumericVector/Matrix。 但是,我现在需要一个 Cholesky decomp/solve:我知道该怎么做 使用 RcppEigen 但我需要VectorXd/MatrixXd's。假设我有 P.S.D. NumericMatrix, A 和 NumericVector, b。我尝试了以下各种变化:

  Rcpp::NumericVector b(bb);
  Rcpp::NumericMatrix A(AA);
  Eigen::Map<Eigen::MatrixXd> A_eigen = as<Eigen::Map<Eigen::MatrixXd> >(A);
  Eigen::Map<Eigen::VectorXd> b_eigen = as<Eigen::Map<Eigen::VectorXd> >(b);
  Eigen::LLT<Eigen::MatrixXd> llt(A_eigen);
  Eigen::VectorXd x = llt.solve(b_eigen);
  Rcpp::NumericVector xx(wrap(x));
  return xx;

然后可以使用inline 包编译它(这里用codeString 表示),如下所示:

f = cxxfunction(signature(AA="matrix",bb="numeric"),codeString,plugin="RcppEigen")

我知道我可以直接从 SEXP 实例中获取 Eigen::MatrixXd/VectorXd(例如使用 Eigen::Map),但在我的使用中我需要从 NumericMatrix/Vector 实例中获取这些。

我的 A 会很小,所以我不会太小 担心是否会创建完整副本。如果有人能提供一个笨重的 解决方案,这将是一个很好的解决方案,一个优雅的解决方案将是 太好了!

在此先感谢您,也感谢您在 Rcpp(Eigen) 上所做的所有出色工作,

大卫

【问题讨论】:

您能否提供一个完整的可重现示例。并且可能显示你得到的编译器错误。 嗨罗曼 - 感谢您的回复。希望我添加的内容有所帮助。 【参考方案1】:

查看 RcppEigen 源和文件 src/fastLm.hsrc/fastLm.cpp

他们通过多种不同的分解方法建立了一个非常好的工厂。请注意,对于每个已实施的求解器,结果始终是受保护的 VectorXd m_coef(即 Eigen 类型),它仅在最后被转换:

        // Copy coefficients and install names, if any
NumericVector     coef(wrap(ans.coef()));
List          dimnames(NumericMatrix(Xs).attr("dimnames"));

完全可以想象,我们可以用不同的方式来做这件事——但是这个例子已经运行了很长一段时间了。我只会跟着它。

【讨论】:

谢谢!结合使用 `as' 去另一个方向做我需要的。【参考方案2】:

Choleski 分解是在 base 中实现的。 Here 是文档的链接。如果我理解错了,那么也许你可以自己写一个?查看thisRosetta 代码链接,了解多种语言的 Choleski 分解,为您提供建议。

【讨论】:

以上是关于在 Rcpp(Eigen) 中的 NumericVector/Matrix 和 VectorXd/MatrixXd 之间转换以执行 Cholesky 求解的主要内容,如果未能解决你的问题,请参考以下文章

降价中的 Rcpp

MAGMA 和 Rcpp 用于 R 中的线性代数

Rcpp犰狳中的样本

Rcpp 程序中的最小值和最大值

犰狳中的 Rcpp 糖命令

如何从 Rcpp 中的另一个函数调用一个函数?