c++ - 在 C++ 项目中设置 R (C api)
问题描述
我想在我自己的 cpp 项目中使用 R 包(AlgDesign - https://github.com/jvbraun/AlgDesign/tree/master/src )的 cpp 功能。
我常用的 IDE 是 Visual Studio 2015。我发现这篇相关的帖子Building R packages (C API) with Visual Studio(以及How do I compile a dll with R and RCPP?)所以我在 Windows 8.1 上安装了 MinGW 和 CodeBlocks IDE 和重试。我将“Rdir/include”路径添加到 CodeBlocks 中的“项目构建选项->搜索目录->编译器”。
但我仍然得到“未定义的引用_GetRNGstate”,它相当于MSVC“未解析的外部符号_GetRNGstate”。所以我猜这个问题是一个缺失的库,就像已经提到的原始提问者一样。但我也不知道是哪一个。我的 R-install 目录中没有 .lib 文件。
此外,我不打算使用 Rcpp 或构建自己的 R 包,我只是想在我自己的 cpp-project 中访问 SEXP FederovOpt(..args) 函数
编辑:假设我想将 AlgDesign src 文件函数逐个函数传输到一个空项目中。在某些时候我会达到这个:
#include "wheeler.h"
#include <string.h>
#include <stdlib.h>
#include <Rinternals.h>
#include <Rdefines.h>
#include <R.h>
#include <Rmath.h>
#include <R_ext/RS.h>
#include <R_ext/Utils.h>
/* Permute **********************************************************
| Randomly pemutes the n integers in a[] using the Fike
| algorithm. See Fike, "A permutation generation method" The Computer
| Journal, 18-1, Feb 75, 21-22.
*/
void Permute(
int *a,
int n
)
{
int i,
j,
temp;
GetRNGstate();
for (i = 1; i < n; i++) {
j = (int)((double)(1 + i)*unif_rand());
temp = a[j];
a[j] = a[i];
a[i] = temp;
}
PutRNGstate();
}
int main(){
return 0;
}
我将
在 RC API 的 Random.h 中定义void GetRNGstate(void)
的 RC API 的 Random.h 中定义的 3 个未解析的外部变量在 RC API
void PutRNGstate(void)
的 Random.h 中
double unif_rand(void)
定义
最后,我找到了这篇文章:https ://www.codeproject.com/Questions/1192515/I-want-to-run-R-script-from-Cplusplus-code
所以当然,我正在寻找一个 .lib 文件。但是这个文件在 Windows 中不存在,我必须自己创建 .lib 文件。但我不知道怎么做。我找到了这个,但它很旧,目录完全不同:https ://uploads.cosx.org/2009/12/Integrate-R-into-C.pdf
请你帮助我好吗?一个简单的“轻松使用makefile”或单个cmd命令对我没有帮助,我无法理解。我以前从未使用过makefile,也从未构建过.lib。
解决方案
我看到两种可能的方法:
- 将 R 解释器嵌入到您的应用程序中,例如使用
Rinside
包。然后你可以调用环绕FederovOpt
. - 该
FederovOpt
函数包含了一些执行实际工作的普通 C 函数。它的主要任务是将这些 C 函数与 R 接口。如果您不使用 R,否则您也可以提取这些 C 函数并直接使用它们。
使用哪种解决方案?如果您需要其他 R 功能,1. 可能会更容易。查看 Rinside 附带的示例。您可能必须坚持使用 mingw,最好来自 Rtools。如果这是您需要的唯一 R 功能,那么 2. 可能是要走的路。如果你让代码独立于 R,你可以使用 VS。有些例子做了类似的事情,例如https://github.com/zhanxw/libMvtnorm。在这两种情况下,您都必须遵守 GPL。
为了使选项二更明确,我做了一个简单的测试:
- 下载
FederovOpt.c
和wheeler.h
. - 删除所有
#include
特定于 R 的标头。 - 为and加上
#include <math.h>
and 。#define
TRUE
FALSE
- 删除 R 特定功能
ProgAlloc
,ProgDealloc
以及FederovOpt
- 删除 R 特定的函数调用
R_CheckUserInterrupt()
,GetRNGstate()
和PutRNGstate()
. - 替换
unif_rand()
为rand() / (RAND_MAX + 1.0)
。
生成的文件可以在gcc
没有错误或警告的情况下编译。当添加一个main()
. 在那里,您将分配内存、调用FederovOptimize
并再次释放内存。
顺便说一句,RNG 当然比 R 的 RNG 差得多,但可能足以完成这项任务。使用 C++11,您当然有更好的可能性。
推荐阅读
- sql - 具有唯一值的列的 SQL 总和量
- sql - 解析为表时 Oracle 游标声明不正确
- powerbi - Power BI 固定十进制有两位数,而不是四位
- javascript - angular form.io form-builder 自定义组件获取参考
- python - 具有多个用户名的注册用户 - Django REST
- vb.net - 错误 [HY000] [mysql][ODBC 3.51 driver][mysqld-5.5.5-10.4.14-mariadb]column 'nofak' 不能为空
- json - 颤振:我如何获得列表
从 JSON 响应? - nginx - nginx-prometheus-exporter 容器无法连接到 nginx
- swift - 在 UIImageView 上添加部分遮罩
- node.js - 每当我尝试在 VS Code 中运行任何与 npm 相关的命令时,都会出现路径错误:[找不到模块]