《java调用R软件实现数据分析引擎集成.docx》由会员分享,可在线阅读,更多相关《java调用R软件实现数据分析引擎集成.docx(7页珍藏版)》请在三一办公上搜索。
1、java调用R软件实现数据分析引擎集成Java调用R,就是使用JRI.jar中的Api,执行一条R语言命令,当然首先你要了解R语言的语法。 1.JRI中主要的API Rengine R引擎,通过它进行R语言的启动、运算、画图、关闭等功能。 一个线程只能实例化一次,推荐使用单例模式。 实例化代码: Rengine engine = new Rengine(null,false,null); Rengine.versionCheck /R版本校验,返回true:版本校验通过 返回false:版本校验未通过 engine.waitForR /R加载校验,返回true:加载成功 返回false:加载失
2、败 engine.end /结束R,在后续没有调用R的情况下使用,否则R将退出,不能继续使用R。 2.REXP R计算结果表达式 REXP rexp = engine.eval_r(String str) /执行R命令,返回结果REXP rexp.asInt rexp.asDouble rexp.as. /将REXP转成java类型 engine.assign(String name,double d) /定义R变量,name为R中变量的名字 以上大概了解了JRI的基本API,下面写个简单的例子。 /求n个数的最大值 Rengine engine = new Rengine(null,fals
3、e,null); int arr = new int-1,2,1,-3,5,4,-2; engine.assign(x,arr); REXP rexp = engine.eval_r(max(x); int max = rexp.asInt; System.out.println(max); 太好了,一个简单的例子完成了,我们来试一下吧! 不好意思,这样程序还不能运行,Java调用R需要一个启动参数:/应该就是环境变量 -Djava.library.path=%R_HOME%libraryrJavajri 加上这个启动参数后,终于OK了。 做到这里Java调用R的第一步也是最重要的一步终于完成
4、了。Congratulations! 这只是个简单的例子,在实际使用中可以使用R中较复杂的函数进行统计,个人建议对R的操作封装为一个工具类,以免对唯一的Rengine实例进行了误操作,导致程序整体崩溃。R与JAVA的整合 R是统计计算的强大工具,而JAVA是做应用系统的主流语言,两者天然具有整合的需要。关于整合,一方面,R中可以创建JAVA对象调用JAVA方法,另一方面,JAVA中可以转换R的数据类型调用R的函数,互相取长补短。现在也有一个项目JGR,用JAVA做R的图形界面,可以实现高亮显示自动补全等,还能让JAVA和R互相调用。 关于R中调用JAVA,我想主要是为了利用其面向对象的特性,毕
5、竟R语言近来很致力于向面向对象发展,有个很好的项目rJava可以实现,在 XP、R2.10.1和JDK1.6下完成。 JAVA很适合开发应用系统,但是数学建模和计算能力非其所长,如果该系统需要进行大量的统计或者优化的计算,调用R是一种很好的方式。JAVA负责系统的构建,R用来做运算引擎,从而实现应用型和分析性相结合的系统。 首先要介绍的是Rserve的方式,这是一个基于TCP/IP的服务器,通过二进制协议传输数据,可以提供远程连接,使得客户端语言能够调用R。目前Rserve作为一个package发布在CRAN上,可以直接使用install.packages(Rserve)进行安装。需要使用时在
6、R控制台下加载该包,然后输入命令Rserve,开启服务器,就可以供客户端调用。 其客户端可以有多种,这里只介绍JAVA客户端。最早的客户端包是JRclient,在www.rosuda.org/Rserve上还可以下载到,但是现在该项目全部移到了到REngine.jar和RserveEngine.jar两个文件。如果用eclipse开发的话,在工程属性中导入这两个外部的jar包,就可以正常使用了。 一个简单的例子: java view plain copy print? 1. 2. 3. 4. 5. 6. 7. 8. public class rtest public static void m
7、ain(String args) throws REXPMismatchException, REngineException RConnection c = new RConnection; REXP x = c.eval(R.version.string); System.out.println(x.asString); 另一种方式是JRI,全名是Java/R Interface,这是一种完全不同的方式,通过调用R的动态链接库从而利用R中的函数等。目前该项目已经成了rJava的子项目,不再提供单独的JRI的版本。因此使用时简单地通过install.packages(rJava)安装rJav
8、a就行,在安装文件夹中,可以看到一个jri的子文件夹,里面有自带的例子可以用来测试。 装好后要修改系统的环境变量,在PATH中添加%R_HOME%bin和%R_HOME%libraryrJavajri,注意R_HOME的路径要正确,重启系统使之生效。使用时同样在eclipse里导入外部的jar包,在rJava包安装目录下的jriexamples里有现成的例子,可以测试是否成功。 之前我的电脑上一直存在一个很奇怪的问题,测试第一个例子时在“Creating Rengine (with arguments)”的时候就停住了,第二个例子中一个JAVA框很快闪一下就消失了,控制台中没有任何提示。打开J
9、GR也是一闪即逝。在网上查了很久,只有一个印度哥们也遇到过类似的问题,而且没有找到解决办法。估计应该是实现RMainLoopCallbacks时出了问题,但是找不到原因,后来卸载了R2.9.0重装了R2.10.1,并且通过install.packages安装,终于没问题了,可能是主程序和Package之间的版本冲突,以后记住全部用install.packages来安装package了。 关于客户端服务器的方式和动态链接库的方式,各有所长,按照需要选用。个人经验,不管使用哪种方式,设计时尽量少进行频繁的数据的交互,在逻辑上把系统和计算分开,使得R成为一个纯粹的运算引擎。 Eclipse JRI
10、: Java 调用 R 报错: Cannot find JRI native lib Eclipse JRI : Java 调用 R 报错: Cannot find JRI native library! 具体的解决方法如下: R_HOME = C:Program FilesRR-2.15.0 ( R 的安装主目录) RJAVA_HOME = C:Program FilesRR-2.13.0libraryrJava PATH = %PATH%;%RJAVA_HOME%jrix64;%RJAVA_HOME%jri;%R_HOME%binx64; 另,选择i386,还是x64根据您的实际情况决定!
11、 32电脑i386 备注:可以通过Java直接在 Eclipse里面把 java.library.path 打印出来确认JRI native library! 的文件路径是正确配置的 System.out.println(System.getProperty(java.library.path); 终于调试成功啦! Java调用R_JRI 1. R中需要安装rJava包。 2. 系统变量Path加上 C:Program FilesRR-3.0.1bini386;C:Program FilesRR-3.0.1libraryrJavajri 系统变量Classpath加上: C:Program F
12、ilesRR-3.0.1libraryrJavajriJRI.jar 3. 项目中加入JRI.jar, JRIEngine.jar, REngine.jar 4. 将rJava自带的测试实例,加入项目测试,执行成功。配置完成。 5. Java本地测试 C:Program FilesRR-3.0.1libraryrJavajriexamples有rJava自带的实例 R脚本分条执行,基本语法同Rserve. for循环时需要java变量和R变量的转换。 6. Java Web的lib目录下加入JRI.jar, JRIEngine.jar, REngine.jar C:Program FilesR
13、R-3.0.1libraryrJavajrii386jri.dll放入Java Path中或者Tomcat bin目录中 7. 利用自带实例rtest中的TextConsole方式实例化Rengine对象 class TextConsole implements RMainLoopCallbacks Rengine re=new Rengine(args, false, new TextConsole); 8. 经个人测试,在项目中多次调用Rengine re=new Rengine(args, false, new TextConsole); 会在第二次报错。 最后将Rengine对象实例化
14、改成 单例 模式,项目初始化时一并进行实例化。 对于R中需要加载的外部包,可以一并在实例化re时,执行。 java view plain copy 1. 2. 3. 4. 5. 6. 7. 8. 9. 10. 11. 12. 13. 14. 15. 16. 17. 18. 19. 20. public void callR System.out.println(System.getProperty(java.library.path); System.loadLibrary(jri); try /Rengine re = new Rengine(null, false, new TextCon
15、sole); Rengine re = rengine.getInstance; re.eval(setwd(f:/R_Stat/); re.eval(selected_dat - read.csv(dat.csv,head=TRUE,sep=, , as.is = T); . re.eval(rect(1, 5, 3, 7, col=white); re.eval(dev.off); catch (Exception e) e.printStackTrace; 测试通过。 补充:Rengine的构造设成单例 java view plain copy 1. 2. 3. 4. 5. 6. class rengine private static Rengine re; private rengine public static Rengine getRegineInstance if(re =null) 7. 8. 9. 10. 11. 12. re = new Rengine(null, false, new TextConsole); re.eval(library(arules); return re;