Skip to content


编写R包C扩展的核心指引

以下,$RHOME都是指代你安装R所在的目录。

R的配置文件,在$RHOME/etc下

  • Renviron:环境变量与路径配置,大都可顾名思义,主要介绍以下两个。
    • R_LIBS_SITE: 包搜索路径,在R命令行下可用.libPaths()显示,;
    • R_LIBS_USER: 用户包目录,如果设置为”~/Rlibs/”,则每个用户在没有全局安装权限时,默认地会把包安装到~/Rlibs/下,无需添加到R_LIBS_SITE也能被搜索到,但在R命令行下用.libPaths()不会显示该路径,这样每个用户可以拥有一个自己本地的R库;
    • 如果想配置一个本地测试环境,以便与生产环境区分开,可以在安装包时指定一个路径,如R CMD INSTALL testR.tar.gz -l ~/Rtest 可以把testR包安装到~/Rtest下,写测试文件时第一行加上.libPath(‘~/Rtest’),就可以正确找到testR包了。
  • ldpaths:动态库载入路径配置。
    • R_LD_LIBRARY_PATH:R 包载入时动态库搜索路径,默认为${R_LD_LIBRARY_PATH=${R_HOME}/lib:},如果要加上/usr/local/lib,则 变为${R_LD_LIBRARY_PATH=${R_HOME}/lib:/usr/local/lib:}
  • Makeconf:包编译链接配置,类似于Makefile,可被用户引用或重载。在R CMD INSTALL/build时使用。
    • 如果使用Makevars文件,则把该文件放到包的src目录下,文件中的配置可使用并扩展Makeconf的配置。
    • 例 子:在Makevars中定义PKG_LIBS = -L/usr/local/lib -lmylibs $(LAPACK_LIBS) $(BLAS_LIBS),其中$(LAPACK_LIBS)与$(BLAS_LIBS)是Makeconf中预定义的变量,这里定义的PKG_LIBS变量会被Makeconf中的ALL_LIBS变量所使用,作为链接参数的一部分。
  • repositories:cran站点。

R的头文件在$RHOME/include,对于用C写R扩展这个应用场景来说,有用的是R.h,Rdefines.h和Rinternals.h这几个文件。

  • R.h是每一个为R作接口的C扩展里必须包含的。
  • Rinternals.h是最核心的定义文件,它定义了最基本也是唯一的R结构SEXP(详见这里)及其它的一些数据类型与结构、常量、以及所有你会用得到的接口函数。
  • Rdefines.h中include了Rinternals.h,并且为了方便使用,定义了一大批的宏,对Rinternals.h中的函数进行了封装,虽然还不是完全的封装,但已经很够用,语义上也好理解得多。

Rdefines.h中一些常用的R扩展函数,让你可以在C里操作R的数据结构,以下的函数参数x的类型都是SEXP,n为int型变量:

  • AS_XXX:类型转换,等同于R中的as()函数。如AS_INTEGER(x)把x转换为INTEGER类。类似的还有IS_XXX,等同于R中的is()函数。
  • NEW_XXX:生成一个向量对象,如NEW_INTEGER(n)生成一个长度为n的向量,SEXP类型。通过NEW_OBJECT(MAKE_CLASS(“classname”))可生成任意一个类的对象。
  • XXX_POINTER:取得SEXP向量对象数据的指针,如INTEGER_POINTER(x)返回指向x的数据的指针,接下来可以在C里自由操作。
  • mkString:比较简便地生成一个字符串型SEXP对象的方法,如mkString(“xyz”)。
  • GET_ATTR, SET_ATTR, GET_SLOT, SET_SLOT:获取/设置对象属性,获取/设置对象SLOT,可参考文件中的定义。
  • allocVector, allocMatrix:生成一个向量/矩阵,在Rinternals.h中定义。
  • NEW_LIST, SET_ELEMENT:list相关的操作。
  • PROTECT, UNPROTECT:为避免被R的垃圾回收机制错误回收,在用NEW_XXX或alloc*分配内存生成对象时,需要用PROTECT()函数括起来,最后用UNPROTECT(n)取消保护,n的个数应该等于之前PROTECT函数被使用过的次数。
收藏或分享到:
  • Print
  • Digg
  • del.icio.us
  • Facebook
  • Google Bookmarks
  • FriendFeed
  • Twitter

Posted in Programming.

Tagged with .


0 Responses

Stay in touch with the conversation, subscribe to the RSS feed for comments on this post.



Some HTML is OK

or, reply to this post via trackback.