使用 Rcpp 运行编译的 C++ 代码

2024-01-10

我一直在努力通过 Dirk Eddelbuettel 的方法Rcpp教程在这里:

http://www.rinfinance.com/agenda/ http://www.rinfinance.com/agenda/

我已经学会了如何将 C++ 文件保存在目录中并调用它并从 R 中运行它。我正在运行的 C++ 文件称为“logabs2.ccp”,其内容直接来自 Dirk 的一张幻灯片:

#include <Rcpp.h>

using namespace Rcpp;

inline double f(double x) { return ::log(::fabs(x)); }

// [[Rcpp::export]]
std::vector<double> logabs2(std::vector<double> x) {
    std::transform(x.begin(), x.end(), x.begin(), f);
    return x;
}

我用这个 R 代码运行它:

library(Rcpp)
sourceCpp("c:/users/mmiller21/simple r programs/logabs2.cpp")
logabs2(seq(-5, 5, by=2))
# [1] 1.609438 1.098612 0.000000 0.000000 1.098612 1.609438

我正在 Windows 7 计算机上从似乎默认安装的 R GUI 中运行代码。我还安装了最新版本Rtools。上面的R代码看起来运行时间比较长。我怀疑大部分时间都花在了编译 C++ 代码上,并且一旦编译了 C++ 代码,它就会运行得非常快。Microbenchmark当然表明Rcpp减少计算时间。

到目前为止我从未使用过 C++,但我知道当我编译 C 代码时我会得到一个 *.exe 文件。我从一个名为的文件中搜索了我的硬盘驱动器logabs2.exe但找不到。我想知道上面的 C++ 代码是否会运行得更快,如果logabs2.exe文件已创建。是否有可能创建一个logabs2.exe文件并将其存储在某个文件夹中,然后让 Rcpp 在我想使用它时调用该文件?我不知道这是否有道理。如果我可以将 C++ 函数存储在 *.exe 文件中,那么也许我不必每次想将它与 Rcpp 一起使用时都编译该函数,然后 Rcpp 代码可能会更快。

抱歉,如果这个问题没有意义或重复。如果可以将 C++ 函数存储为 *.exe 文件,我希望有人能告诉我如何修改上面的 R 代码来运行它。感谢您对此提供的任何帮助,或者让我明白为什么我的建议是不可能或不推荐的。

我期待看到德克的新书。


感谢 user1981275、Dirk Eddelbuettel 和 Romain Francois 的回复。下面是我如何编译 C++ 文件并创建 *.dll,然后在内部调用并使用该 *.dll 文件R.

步骤 1. 我创建了一个名为“c:\users\mmiller21\myrpackages”的新文件夹,并将文件“logabs2.cpp”粘贴到该新文件夹中。文件“logabs2.cpp”是按照我原来的帖子中所述创建的。

步骤 2. 在新文件夹中我创建了一个新的R名为“logabs2”的包使用R我编写的文件名为“新包创建.r”。 “新包创建.r”的内容是:

setwd('c:/users/mmiller21/myrpackages/')

library(Rcpp)

Rcpp.package.skeleton("logabs2", example_code = FALSE, cpp_files = c("logabs2.cpp"))

我发现上面的语法Rcpp.package.skeleton在 Hadley Wickham 的网站之一上:https://github.com/hadley/devtools/wiki/Rcpp https://github.com/hadley/devtools/wiki/Rcpp

步骤 3. 我安装了新的R包“logabs2”在R在 DOS 命令窗口中使用以下行:

C:\Program Files\R\R-3.0.1\bin\x64>R CMD INSTALL -l c:\users\mmiller21\documents\r\win-library\3.0\ c:\users\mmiller21\myrpackages\logabs2

where:

rcmd.exe 文件的位置是:

C:\Program Files\R\R-3.0.1\bin\x64>

安装位置R我电脑上的软件包是:

c:\users\mmiller21\documents\r\win-library\3.0\

以及我的新位置R安装之前的包是:

c:\users\mmiller21\myrpackages\

DOS 命令窗口中使用的语法是通过反复试验发现的,可能并不理想。在某些时候,我将“logabs2.cpp”的副本粘贴到“C:\Program Files\R\R-3.0.1\bin\x64>”中,但我认为这并不重要。

步骤 4. 安装新版本后R包我使用运行它R我在“c:/users/mmiller21/myrpackages/”文件夹中将其命名为“new package use.r”(尽管我认为该文件夹并不重要)。 ‘new package use.r’的内容是:

library(logabs2)
logabs2(seq(-5, 5, by=2))

输出是:

# [1] 1.609438 1.098612 0.000000 0.000000 1.098612 1.609438

该文件加载了包Rcpp不用我问。

在这种情况下基R假设我正确执行了此操作,速度会更快。

#> microbenchmark(logabs2(seq(-5, 5, by=2)), times = 100)
#Unit: microseconds
#                        expr    min     lq  median     uq     max neval
# logabs2(seq(-5, 5, by = 2)) 43.086 44.453 50.6075 69.756 190.803   100

#> microbenchmark(log(abs(seq(-5, 5, by=2))), times=100)
#Unit: microseconds
#                         expr    min     lq median    uq     max neval
# log(abs(seq(-5, 5, by = 2))) 38.298 38.982 39.666 40.35 173.023   100

但是,使用 dll 文件比调用外部 cpp 文件更快:

system.time(

cppFunction("
NumericVector logabs(NumericVector x) {
    return log(abs(x));
}
")

)

#   user  system elapsed 
#   0.06    0.08    5.85 

尽管在本例中,基本 R 似乎更快或与 *.dll 文件一样快,但我毫不怀疑将 *.dll 文件与Rcpp会比基础更快R在多数情况下。

这是我第一次尝试创建 R 包或使用 Rcpp,毫无疑问我没有使用最有效的方法。另外,我对这篇文章中的任何印刷错误表示歉意。

EDIT

在下面的评论中,我认为 Romain Francois 建议我将 *.cpp 文件修改为以下内容:

#include <Rcpp.h>
using namespace Rcpp;

// [[Rcpp::export]]

NumericVector logabs(NumericVector x) {
return log(abs(x));
}

并重新创建我的R包,我现在已经完成了。然后我比较了基础R使用以下代码针对我的新包:

library(logabs)

logabs(seq(-5, 5, by=2))
log(abs(seq(-5, 5, by=2)))

library(microbenchmark)

microbenchmark(logabs(seq(-5, 5, by=2)), log(abs(seq(-5, 5, by=2))), times = 100000)

Base R仍然快一点或者没有什么不同:

Unit: microseconds
                         expr    min     lq median     uq       max neval
   logabs(seq(-5, 5, by = 2)) 42.401 45.137 46.505 69.073 39754.598 1e+05
 log(abs(seq(-5, 5, by = 2))) 37.614 40.350 41.718 62.234  3422.133 1e+05

也许这是因为基地R已经矢量化了。我怀疑有更复杂的功能基础R会慢很多。或者也许我仍然没有使用最有效的方法,或者也许我只是在某个地方犯了错误。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

使用 Rcpp 运行编译的 C++ 代码 的相关文章

  • 在 std::forward 中它如何接受右值?

    看看斯科特 迈耶的有效的现代 C 第200 201页 建议的简化实施std forward可能是 在其他地方看到了正确的实现 template
  • C# 中 value 为匿名类型的字典

    是否可以在 C 中创建一个System Collections Generic Dictionary
  • 在 C++ 中从另一个数组初始化结构内的数组[关闭]

    这个问题不太可能对任何未来的访客有帮助 它只与一个较小的地理区域 一个特定的时间点或一个非常狭窄的情况相关 通常不适用于全世界的互联网受众 为了帮助使这个问题更广泛地适用 访问帮助中心 help reopen questions struc
  • WPF 中可选择的 TextBlock 或带有格式化文本的 TextBox

    我遇到一种情况 我需要显示格式化文本 正常 粗体 突出显示 并且还应该是可选择的 以便用户可以复制文本 我使用了文本块 我可以使用内联内容流元素应用多种格式 但不幸的是它的文本不可选择 虽然文本框允许选择文本并复制到剪贴板 但它不允许我设置
  • boost变体简单调用常用方法

    我有两个指针 只能设置其中之一 所以我正在考虑使用 boost variant 例如 boost variant
  • 将私有部分保留在 C++ 标头之外:纯虚拟基类与 pimpl

    我最近从 Java 和 Ruby 切换回 C 令我惊讶的是 当我更改私有方法的方法签名时 我必须重新编译使用公共接口的文件 因为私有部分也位于 h 文件中 我很快想出了一个解决方案 我想这对于 Java 程序员来说是典型的 接口 纯虚拟基类
  • 给出对象的指针作为参数

    假设我有 void func foo obj 我有 foo object 我该如何制作object进入争论func 只需取消引用它即可 func object
  • 为什么泛型 IList<> 不继承非泛型 IList

    IList
  • 是否可以旋转 R 中的绘图(基本图形)?

    我搜索了这个 发现使用 grid 有多种方法可以旋转图像 并且对于某些绘图 您可以使用它们的旋转 例如plot x y 而不是plot y x 不过我想知道是否有R 中旋转绘图的通用方法 适用于基础图形中生成的任何绘图 您可以导出图形 将其
  • 等效

    这是否保证始终为真 std numeric limits
  • 如何从 MongoDB 中的 ChangeStream 过滤对特定字段的更新

    我正在设置一个 ChangeStream 以便在集合中的文档发生更改时通知我 以便我可以将该文档的 LastModified 元素更新插入到事件发生的时间 由于此更新将导致 ChangeStream 上发生新事件 因此我需要过滤掉这些更新以
  • BlueZ D-Bus C,应用 BLE

    我正在尝试编写一个应用程序来搜索附近的蓝牙设备并与它们通信 我的应用程序将用 C 语言编写 并打算在 Linux 下工作 是否有通过 C 中的 D Bus 使用 BlueZ 的教程或示例 此应用程序的目的是从 BLE 中的文件发送数据 你能
  • 对嵌套属性使用 XmlAttributeOverrides

    我试图使用 XmlAttributeOverrides 来控制类序列化后哪些类属性出现在 xml 中 它适用于 根 类上的属性 但不适用于嵌套属性 这是一个简单的例子来说明我想要完成的任务 我的类层次结构如下 public class Ma
  • 使用“kde”函数进行 R 中的 5-D 核密度估计

    我想通过使用 R 的 ks 库中的 kde 函数来执行 5 维数据 x y z 时间 大小 的核密度估计 在它的手册中 它说它可以执行核密度估计1 至 6 维数据 手册第 24 页 http cran r project org web p
  • System.IndexOutOfRangeException:索引超出了数组的范围[重复]

    这个问题在这里已经有答案了 我正在开发一个 ATM 软件作为家庭作业 我想知道今天处理的交易总量 为此我编写了以下代码 public decimal getDayTransaction int accountid string date s
  • R Markdown 文档标题中的希腊字母

    R markdown 文档的标题中是否可以包含希腊字母 我试过这个 title Amylase author author date 8 March 2017 output pdf document keep tex true toc ye
  • 以编程方式连接和断开 USB,“无需拔出和重新插入”

    我需要以编程方式连接和断开 USB 也就是说 我已经插入了USB设备 我需要使用 C NET 应用程序传输文件 该应用程序将监视特定文件夹并将文件从该文件夹传输到 USB 驱动器 我需要在文件传输后断开 USB 设备的连接 并在需要时连接
  • C++ 从文件中读取字符串

    我试图将字符串直接存储到一个文件中 以便稍后在 C 中读取 基本上 对于整个范围 我试图将带有字符串变量的对象数组存储在文件中 并且这些字符串变量将通过类似 object 的内容读取 0 字符串 然而 每次我尝试读取字符串变量时 系统都会给
  • wpf中的图像问题(图像不显示)

    我不明白为什么我无法在 WPF 中显示图像 也许我不小心修改了我的资源文件夹 这就是我没有显示的原因 所以我创建了一个新的 wpf 应用程序 我有这个 当我运行该程序时 我的图片显示为 为什么当我尝试在程序中执行相同的操作时 图像没有显示
  • 文件按文件名模式存在

    我在用 File Exists filepath 我想做的是将其替换为模式 因为文件名的第一部分发生了变化 例如 该文件可以是 01 peach xml 02 peach xml 03 peach xml 如何根据某种搜索模式检查文件是否存

随机推荐

  • 计算两个角度之间的绝对差

    我有两个角度a和b 我想计算两个角度之间的绝对差 例子 gt gt absDiffDeg 360 5 ans 5 gt gt absDiffDeg 5 5 ans 10 gt gt absDiffDeg 5 5 ans 10 标准化差异 a
  • 如何使用 Selenium WebDriver 查找嵌套跨度中的元素?

    我正在尝试单击跨度 n6 中的 新交易 链接 该跨度 n6 是跨度 n2 的子元素 我能够到达 n2 但它无法识别 n6 请帮助我是 Selenium WebDriver 的新手 在这里我发布了 html 和我的代码 Trading 新的
  • 函数式 Scala 的重构/布局

    这一班班轮 Console println io Source fromFile names txt getLines mkString split map x String gt x slice 1 x length 1 sortBy x
  • KITTI校准文件中参数的格式

    我从以下位置访问了校准文件KITTI 的部分里程计 http www cvlibs net datasets kitti eval odometry php 其中一个校准文件的内容如下 P0 7 188560000000e 02 0 000
  • 根据数据类型对 WPF DataGrid 单元格进行条件格式化

    我有一个继承自 WPF DataGrid 控件的用户控件 并向其传递不同的对象列表 因此 网格的列取决于 即自动生成 我发送的对象的类
  • 如何从createQueryBuilder获取sql?

    你知道我如何从 createQueryBuilder 获取 sql 吗 我的 Entity DownloadRepository php 类 public function getLastDownload limit query this
  • Npm 发布到私有范围总是失败

    我最近创建了一个新组织 并选择了付费计划来发布无限的私人包 但是 每次我尝试将包发布到我的组织时 它都会不断出现以下错误 npm ERR publish Failed PUT 403 npm ERR code E403 npm ERR Fo
  • android - 如何在活动完成后显示对话框

    假设我们有两个活动 Activity1 和 Activity2 在 Activity1 的 onClick 方法中 如果按下某个按钮 我们会调用启动 Activity 2 Intent myIntent new Intent Activit
  • 我如何使用java发送电子邮件而不进行身份验证

    我想使用java发送电子邮件而不进行身份验证 有人能帮我吗 通过身份验证 我按如下方式执行 public void sendEmail throws EmailException SimpleEmail email new SimpleEm
  • 打字稿错误:Object.fromEntries 打字稿错误

    我在打字稿中有一个函数 它使用 Object fromEntries 来减少复杂的响应对象 并使用子对象键的子字符串对其进行分组 let Newresult res map object gt Object fromEntries Obje
  • BackgroundWorker 不会在 CancelAsync() 上停止并且仅工作一次

    我有一种名为 Sorter 的表单 其上有 jademy 按钮 可打开 进度窗口 窗口 private void jademy Click object sender EventArgs e ProgressWindow progress
  • 将 exec 与 heroku 捆绑在一起 - 有必要吗?

    我最近在 Heroku 上设置了一个 Cedar Rails 3 1 应用程序 并且要运行例如迁移 您需要这样做 heroku run rake db migrate 我了解到在任何 rake 命令之前使用 bundle exec 是一个很
  • aplay 使用文件而不是 stdin 和 stdout 通过管道传输到 arecord

    下面的命令将记录来自默认设备的数据并将其输出到 stdout aplay 将播放来自 stdin 的数据 arecord D hw 0 aplay D hw 1 为什么我们更喜欢 stdin 和 stdout 而不是如下所示写入文件并从中读
  • 如何确定 Excel 工作簿中有多少个工作表?

    在此先感谢您的帮助 我想循环浏览工作簿中的所有工作表 不幸的是 我不知道给定的工作簿中有多少个工作表 现在我使用以下技术来枚举所有工作表 Excel Worksheet xlWorkSheet1 xlWorkSheet1 Excel Wor
  • Google 如何归档文档对象?

    Google 如何存储和组织文档 例如 Google 文档中的文档 我想问Google使用哪种文件系统 但我知道它使用GFS 一种用于存储巨大文件的分布式文件系统 基本上是包含我感兴趣的文档的大型数据库 我的问题是 每个文档都是数据库中的一
  • 如何在mysql中找到第二高的工资

    如何在mysql中找到第二高的工资 所有记录均位于第二高薪水 Table Employee ID salary emp name 1 400 A 2 800 B 3 300 C 4 400 D 4 400 C Mysql Query SEL
  • 每个片段的自定义选项菜单

    我有个问题 我正在尝试更改默认选项菜单 每个片段都不同 我为每个片段创建了一个 xml 文件 并将它们放入 res menu 文件夹中 现在我不知道如何告诉 android 更改每个片段中的默认选项菜单 我将片段放入寻呼机视图中 我所说的菜
  • 有没有办法覆盖 firebase 存储中保存的文件?

    我正在我的 ionic 1 应用程序中处理个人资料图片 我正在寻找一种方法来更新 firebase 存储中的文件 以便下载链接保持不变 是否有可能或任何其他方式来实现所需的 您无法更新该文件并维护相同的公共下载链接 这是一个不同的文件 因此
  • NLTK punkt 的训练数据格式

    我想跑步nltk Punkt来分割句子 没有训练模型 所以我单独训练模型 但我不确定我使用的训练数据格式是否正确 我的训练数据是每行一个句子 我找不到任何关于此的文档 只有这个线程 https groups google com forum
  • 使用 Rcpp 运行编译的 C++ 代码

    我一直在努力通过 Dirk Eddelbuettel 的方法Rcpp教程在这里 http www rinfinance com agenda http www rinfinance com agenda 我已经学会了如何将 C 文件保存在目