首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
社区首页 >问答首页 >Rcpp中的矩阵乘法

Rcpp中的矩阵乘法
EN

Stack Overflow用户
提问于 2016-05-12 15:43:03
回答 3查看 7.4K关注 0票数 14

首先,我是一个新手,所以忘记我一般的无知吧。我正在寻找一个更快的替代R中的%*%运算符的方法。尽管以前的帖子建议使用RcppArmadillo,但我已经尝试了2个小时,试图让RcppArmadillo工作,但没有成功。我总是遇到词汇问题,产生“意想不到的.”错误。我在Rcpp中找到了以下函数,我做的这些函数可以工作:

代码语言:javascript
运行
AI代码解释
复制
library(Rcpp)
func <- '
NumericMatrix mmult( NumericMatrix m , NumericMatrix v, bool  byrow=true )
{
  if( ! m.nrow() == v.nrow() ) stop("Non-conformable arrays") ;
  if( ! m.ncol() == v.ncol() ) stop("Non-conformable arrays") ;

  NumericMatrix out(m) ;

  for (int i = 0; i < m.nrow(); i++) 
  {
  for (int j = 0; j < m.ncol(); j++) 
  {
  out(i,j)=m(i,j) * v(i,j) ;
  }
  }
  return out ;
}
'

但是,此函数执行逐个元素的乘法,其行为与%*%不同。有没有一种简单的方法来修改上面的代码来达到预期的结果?

编辑:

我想出了一个使用RcppEigen的函数,它似乎比%*%更快:

代码语言:javascript
运行
AI代码解释
复制
etest <- cxxfunction(signature(tm="NumericMatrix",
                           tm2="NumericMatrix"),
                 plugin="RcppEigen",
                 body="
NumericMatrix tm22(tm2);
NumericMatrix tmm(tm);

const Eigen::Map<Eigen::MatrixXd> ttm(as<Eigen::Map<Eigen::MatrixXd> >(tmm));
const Eigen::Map<Eigen::MatrixXd> ttm2(as<Eigen::Map<Eigen::MatrixXd> >(tm22));

Eigen::MatrixXd prod = ttm*ttm2;
return(wrap(prod));
                 ")

set.seed(123)
M1 <- matrix(sample(1e3),ncol=50)
M2 <- matrix(sample(1e3),nrow=50)

identical(etest(M1,M2), M1 %*% M2)
[1] TRUE
res <- microbenchmark(
+   etest(M1,M2),
+   M1 %*% M2,
+   times=10000L)

res

Unit: microseconds
         expr    min    lq      mean median     uq    max neval
 etest(M1, M2)  5.709  6.61  7.414607  6.611  7.211 49.879 10000
     M1 %*% M2 11.718 12.32 13.505272 12.621 13.221 58.592 10000
EN

回答 3

Stack Overflow用户

发布于 2016-05-13 10:48:38

有充分的理由依赖现有的库/包来执行标准任务。库中的例程是

  • optimized
  • thoroughly测试了
  • 是一种保持代码紧凑、人类可读和易于维护的好方法。

因此,我认为在这里使用RcppArmadillo或RcppEigen应该更好。然而,为了回答你的问题,下面是一个执行矩阵乘法的可能的Rcpp代码:

代码语言:javascript
运行
AI代码解释
复制
library(Rcpp)
cppFunction('NumericMatrix mmult(const NumericMatrix& m1, const NumericMatrix& m2){
if (m1.ncol() != m2.nrow()) stop ("Incompatible matrix dimensions");
NumericMatrix out(m1.nrow(),m2.ncol());
NumericVector rm1, cm2;
for (size_t i = 0; i < m1.nrow(); ++i) {
    rm1 = m1(i,_);
    for (size_t j = 0; j < m2.ncol(); ++j) {
      cm2 = m2(_,j);
      out(i,j) = std::inner_product(rm1.begin(), rm1.end(), cm2.begin(), 0.);              
    }
  }
return out;
}')

让我们测试一下:

代码语言:javascript
运行
AI代码解释
复制
A <- matrix(c(1:6),ncol=2)
B <- matrix(c(0:7),nrow=2)
mmult(A,B)
#     [,1] [,2] [,3] [,4]
#[1,]    4   14   24   34
#[2,]    5   19   33   47
#[3,]    6   24   42   60
identical(mmult(A,B), A %*% B)
#[1] TRUE

希望这能有所帮助。

正如基准测试所显示的,上面的Rcpp代码比R的内置%*%操作符要慢。我假设,虽然我的Rcpp代码肯定可以改进,但在性能方面很难击败%*%背后的优化代码:

代码语言:javascript
运行
AI代码解释
复制
library(microbenchmark)
set.seed(123)    
M1 <- matrix(rnorm(1e4),ncol=100)
M2 <- matrix(rnorm(1e4),nrow=100)
identical(M1 %*% M2, mmult(M1,M2))
#[1] TRUE
res <- microbenchmark(
             mmult(M1,M2),
             M1 %*% M2,
             times=1000L)
#> res 
#Unit: microseconds
#          expr      min        lq      mean    median        uq      max neval cld
# mmult(M1, M2) 1466.855 1484.8535 1584.9509 1494.0655 1517.5105 2699.643  1000   b
#     M1 %*% M2  602.053  617.9685  687.6863  621.4335  633.7675 2774.954  1000  a
票数 12
EN

Stack Overflow用户

发布于 2016-05-12 16:15:13

我鼓励你尝试用RcppArmadillo解决你的问题。使用它与此示例一样简单,也是通过调用RcppArmadillo.package.skeleton()创建的

代码语言:javascript
运行
AI代码解释
复制
// another simple example: outer product of a vector, 
// returning a matrix
//
// [[Rcpp::export]]
arma::mat rcpparma_outerproduct(const arma::colvec & x) {
    arma::mat m = x * x.t();
    return m;
}

// and the inner product returns a scalar
//
// [[Rcpp::export]]
double rcpparma_innerproduct(const arma::colvec & x) {
    double v = arma::as_scalar(x.t() * x);
    return v;
}

示例中实际上有更多的代码,但这应该会让您有所了解。

票数 5
EN

Stack Overflow用户

发布于 2020-12-21 15:33:02

也可以使用以下方法:

代码语言:javascript
运行
AI代码解释
复制
NumericMatrix mmult(NumericMatrix m, NumericMatrix v)
{
  Environment base("package:base");
  Function mat_Mult = base["%*%"];
  return(mat_Mult(m, v));
}

在这种方法中,我们使用R的运算符%*%。

票数 -1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/37191673

复制
相关文章
Qt中关闭窗口最大化按钮,固定大小
作者:admin,发布日期:2017-02-20 阅读:164;评论:0 效果 image.png 代码: w.setWindowFlags(Qt::WindowCloseButtonHint|Qt::WindowMinimizeButtonHint); 固定大小只要修改以下两条属性即可 image.png
繁花云
2018/07/31
2.4K0
Qt中关闭窗口最大化按钮,固定大小
原创 | matplotlib画图教程,设置坐标轴标签和间距
在上周的文章当中我们介绍了如何通过xlabel和ylabel设置坐标轴的名称,以及这两个函数的花式设置方法,可以设置出各种各样的名称显示方法。今天我们来介绍介绍其他的设置。
TechFlow-承志
2020/09/22
2.2K0
原创 | matplotlib画图教程,设置坐标轴标签和间距
164. 最大间距
桶排序,时间复杂度O(N+C),N=排序对象个数,C=桶的个数。这题中相邻的两个数有两种情况:1)落在同一个桶里 2)小的那个是前一个桶的最大值大的那个是后一个痛的最小值。因为本题中我们桶大小和桶数量都+1了,所以会是2)种情况。
张伦聪zhangluncong
2022/10/26
5570
antd table 设置固定高度
我再使用antd 的table ,现在有个弹窗,弹框里有列表table,发现设置完是这个样子。
星宇大前端
2022/03/09
4.4K0
antd table 设置固定高度
Element 中根据屏幕大小动态计算表格高度以实现固定表头
在Element UI的表格组件中,要想固定表头,必须给表格指定一个高度,但是用户的屏幕大小是不一样的,为了能将表格底部的分页区域始终显示在屏幕内,就需要动态计算表格的高度。
越陌度阡
2021/02/01
2.5K0
varchar有最大长度限制吗
先说结论,mysql 中的 varchar 是有最大长度限制的,这个值是 65535 个字节。
谭小谭
2020/01/15
16.1K0
LeetCode164. 最大间距
 这道题用到了桶排序的思想,但是跟排序没啥关系,思路是这样的,数组中有n个元素,那么就构建n+1个桶,桶的属性有三个,最大值最小值以及是否为空。桶的下标从0到n,然后遍历一遍数组,将其中最小值放到0号桶的位置,最大值放到n号桶的位置,这样的话1~n-1号桶应该放什么数就很清楚了,然后再遍历一遍数组,将其中的所有元素放至应该放到的桶内,并且维护桶的属性,即每个桶的最大值和最小值以及是否为空  最后遍历一遍桶,用当前桶的最小值减去上一个桶的最大值,找到最大的那个数即是答案
mathor
2018/08/17
1K0
LeetCode164. 最大间距
推导B树的最大高度和最小高度得出B树的高度范围
对于任意树类型的数据结构,如果其每层节点能够分布的足够满,其高度也会随之变得足够的低。基于这个思路,对于B树无外乎也是一种树,B树的关键字数以及儿子节点个数满足这样的条件(ceil代表向上取整):
lexingsen
2022/02/24
3.3K0
推导B树的最大高度和最小高度得出B树的高度范围
matplotlib图形的绘制
matplotlib是Python编程语言及其数值数学扩展包 NumPy的可视化操作界面。它利用通用的图形用户界面工具包,如Tkinter, wxPython, Qt或GTK+,向应用程序嵌入式绘图提供了应用程序接口(API)。此外,matplotlib还有一个基于图像处理库(如开放图形库OpenGL)的pylab接口,其设计与MATLAB非常类似--尽管并不怎么好用SciPy就是用matplotlib进行图形绘制。
用户8346838
2021/03/10
2.3K0
如何处理图片的大小?像素和尺寸有区别吗?
现代人的生活当中少不了的一项技能就是图片编辑和修理功能。在发朋友圈或者社交平台的时候,人们总是把拍到的图片进行一系列的修图和美化,然后才上传到社交平台上面,每一个人多多少少都会一些基本的图片处理功能。但是也有一些人对于处理图片是不太精通的,现在来了解一下如何处理图片的大小。
用户8715145
2021/12/30
2.4K0
数据科学 IPython 笔记本 8.11 多个子图
有时,并排比较不同的数据视图会很有帮助。为此,Matplotlib 具有子图的概念:可以在单个图形中一起存在的较小轴域分组。这些子图可能是插图,绘图网格或其他更复杂的布局。在本节中,我们将探讨在 Matplotlib 中创建子图的四个例程。
ApacheCN_飞龙
2022/05/07
1.1K0
数据科学 IPython 笔记本 8.11 多个子图
LeetCode-164. 最大间距(Java)
       哈喽,小伙伴们,我是bug菌呀👀。金三银四,又到了刷题月啦。所以不管你是准备跳槽还是在职,都一起行动起来,顺应这个时代月干点该干的事儿👣。所以,赶紧跟着bug菌的步伐卷起来吧⏰,变强从这一刻开始!➕🧈
bug菌
2023/08/24
1360
LeetCode-164. 最大间距(Java)
无固定高度的div垂直居中
1、无固定高度的div垂直居中 – CSS 实现效果图如下: 代码附上: <!DOCTYPE html> <html> <head> <meta charset="utf-8" /> <meta name="viewport" content="width=device-width,user-scalable=0"> <meta name="apple-mobile-web-app-capable" content="yes">
White feathe
2021/12/08
3.2K0
无固定高度的div垂直居中
内容高度小于窗口高度时版权 div 固定在底部
网站建设中经常遇到文档内容高度小于窗口高度时底部版权 div 固定在底部的问题,纯 css div 底部不太好解决这个问题,这里使用 js 代码来对检测文档高度和窗口高度来实现。
Savalone
2020/02/11
2K0
利用Python绘图和可视化(长文慎入)
Python有许多可视化工具,但是我主要讲解matplotlib(http://matplotlib.sourceforge.net)。此外,还可以利用诸如d3.js(http://d3js.org/)之类的工具为Web应用构建交互式图像。 matplotlib是一个用于创建出版质量图表的桌面绘图包(主要是2D方面)。该项目是由John Hunter于2002年启动的,其目的是为Python构建一个MATLAB式的绘图接口。如果结合使用一种GUI工具包(如IPython),matplotlib还具有诸如缩放
CDA数据分析师
2018/02/05
8.7K0
利用Python绘图和可视化(长文慎入)
matplotlib相关图形绘制(二)
箱线图是由一组数据的最大值、最小值、中位数、两个四分位数(上、下四分位数)这五个特征值绘制而成的,它主要的作用是反应原始数据分布的特征,还可以进行多组数据分布特征的比较。
朱小五
2020/03/05
9800
matplotlib相关图形绘制(二)
纯干货:手把手教你用Python做数据可视化(附代码)
导读:制作提供信息的可视化(有时称为绘图)是数据分析中的最重要任务之一。可视化可能是探索过程的一部分,例如,帮助识别异常值或所需的数据转换,或者为建模提供一些想法。对于其他人来说,构建网络交互式可视化可能是最终目标。Python有很多附加库可以用来制作静态或动态的可视化文件,但是我将主要关注matplotlib和以它为基础的库。
IT阅读排行榜
2018/09/29
5K0
纯干货:手把手教你用Python做数据可视化(附代码)
用数组结构实现大小固定的队列和栈
一.用数组结构实现大小固定的栈 public static class ArrayStack { private Integer[] arr; private Integer size; public ArrayStack(int initSize) { if (initSize < 0) { throw new IllegalArgumentException("The init size is less than 0"); } a
大学里的混子
2019/02/18
1K0
点击加载更多

相似问题

增加matplotlib图形x轴的大小和间距

10

设置固定Matplotlib图形大小高度

249

Matplotlib固定子图高度

43

无间距、受限图形大小和tight_layout()的matplotlib子图

311

最大高度和最大宽度增加图像大小

40
添加站长 进交流群

领取专属 10元无门槛券

AI混元助手 在线答疑

扫码加入开发者社群
关注 腾讯云开发者公众号

洞察 腾讯核心技术

剖析业界实践案例

扫码关注腾讯云开发者公众号
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档
查看详情【社区公告】 技术创作特训营有奖征文