R言語の実行環境を構築し、
rJavaを介してJavaからRを呼び出せるまでの設定を行います。
構築するのは Ubuntu12.04 LTS 上です。
jdkは既に入っているとします。
R言語のインストール
まずはR言語をインストール
$ sudo apt-get update
$ sudo apt-get install r-base
$ sudo apt-get install r-cran-*
で簡単に完了。
apt-getでは本体は /use/lib/R
以下。
$HOME/R
以下にもライブラリなどが入る。
パスを通した方が良いらしいので通す。
$ export R_HOME=/usr/lib/R
参考 : RjpWiki - Rのインストール
rJavaのインストール
JVM関連のパスをRに設定
$ R CMD javareconf
Rを起動して、rJavaをインストール。'J' だけ大文字なので注意。
$ R
> install.packages('rJava')
ミラーサーバを選ぶ画面が出るので適当に選ぶ。( 確かJapan(tsukuba)を選択 )
これで、/usr/lib/R/site-library/
にrJavaフォルダが出来ている。
$HOME/R
の奥深くにもrJavaフォルダが出来ている。
(別環境では、/usr/lib/R/site-liblary/
以下にrJavaフォルダができないこともある。
その時でも、$HOME/R
以下の JRI.jar
を利用することで問題なく連携した。)
参考 : Qiita - jjzak - rjavaのインストールメモ&rincanterの設定(OSX,Ubuntu)
Eclipseで動作確認
Eclipseを入れていなかったので、今回はpleiadesを普通にインストール
$ sudo apt-get install pleiades
改めて動作確認。まずEclipseで普通にプロジェクト作成。
作成途中の「外部jar追加」 で、JRI.jar
を参照。
/usr/lib/R/site-library/rJava/jri/JRI.jar
($HOME/R
以下でも大丈夫)
プロジェクトが出来たら、「デバッグ→デバッグの構成」を開いて、
「引数→VMの引数」に以下を追加
-Djava.library.path=.:/usr/lib/R/site-library/rJava/jri/
また、同じ「デバッグの構成」内の「環境」に、
$R_HOME /usr/lib/R
を追加。
追加しないとRは何処だと怒られる。(上で設定した$R_HOMEは何処へ?)
これで基本的な設定は完了。
mainに以下の参考サイトまんまのコードを書いてデバッグ実行。
package com.test.r;
import org.rosuda.JRI.REXP;
import org.rosuda.JRI.Rengine;
public class RSample {
public static void main(String[] args) {
Rengine engine = new Rengine(new String[]{"--no-save"}, false, null);
engine.assign("a", new int[]{36});
REXP result = engine.eval("sqrt(a)");
System.out.println(result.asDouble());
engine.end();
}
}
コンソールに6.0が出れば完了。
参考 : Symfoware - Ubuntu 12.04にEclipseをインストールする
binfalse - Talking R through Java
hamadakoichi blog - Java R Interface (JRI) を用い 統計解析環境 R を Java から使用する
使い方
R←→Javaのやり取りは、Rengine
というクラスで行います。
assign()
でデータを渡し、
eval()
で関数を実行するらしい。
assignには数値や配列を渡せる。
行列を直接受け取るメソッドが無いので、代わりにREXP
というクラスを渡す。
REXP
クラスとは、RとJavaでのデータ受け渡しに使用されるデータクラスで、
内部でデータ変換をしているものと思われる。
REXP
にはstaticなcreateXXX()
メソッドがあります。
その中に、Double
の2次元配列を受け取りREXP
を吐く仕様があるので、
多分これを利用して行列REXP
を作成し、Rに行列を渡せると思われる。
evalの戻り値もREXP
クラス。
REXP
には asXXXX()
というメソッドが定義されていて、
それによってJava上でXXXの形式で結果が受け取れるらしい。
asVector()
とかasXXXMatrix()
という関数があるので、
行列関係の取得も可能。
注意
Rengine
はSingletonらしく、
2回目以降はnewではなくRengine.getMainEngine();
で
インスタンスを取得する必要がある。