4

プロジェクトにJava/R/Rserveを使用しています。計算のために多次元配列をJavaからRワークスペースに転送するという問題に直面しています。これまでのところ、オブジェクトのassignメソッドではRConnection、次のもののみを渡すことができますbyte[], double[], int[], REXP, String,and String[]

Javaでループを作成することでこれを回避し、変数を個別に渡しました。これは機能しますが、見た目は醜く非効率的です。

RConnection c = new RConnection();
c.eval("x <- matrix(0,nrow=dimX[1],ncol=dimX[2])");
for (int i = 0; i < dimX[0]; i++){
  c.assign("i",Integer.toString(i+1));
  c.eval("i <- as.numeric(i)");
  for (int j = 0; j < dimX[1]; j++){
    c.assign("j",Integer.toString(j+1));
c.eval("j <- as.numeric(j)");
c.assign("tmp", Double.toString(XOBS[i][j]));
c.eval("x[i,j] <- as.numeric(tmp)");
  }             
}

http://www.rforge.net/Rserve/dist/JRclient/JavaDoc/org/rosuda/JRclient/REXP.htmlにあるRserveのドキュメントは古くなっているようで、Rserveの例はかなり限られています。誰かが私にこのコードを改善する方法についての提案を与えることができますか?

ありがとうございました

4

4 に答える 4

2

私は1つの解決策を見つけて、それをもう少し使いやすくしました.ソースへのリンクも添付されています.

コメント: すぐに使えるユーティリティ メソッドです。これは、現在 rJava の一部である JRI に基づいています。

出典:
http://www.lbgi.fr/wikili/index.php/JRI

    /**
     * Creates and assigns a matrix object in R from 2D table of double
     *
     * @param rEngine        the  R instance used
     * @param sourceArray    the 2D table of double
     *                       the matrix must have always the same column number on every row
     * @param nameToAssignOn the R object name
     * @return R matrix instance or null if R return an error
     */
    public static REXP assignAsRMatrix(Rengine rEngine, double[][] sourceArray, String nameToAssignOn) {
        if (sourceArray.length == 0) {
            return null;
        }

        rEngine.assign(nameToAssignOn, sourceArray[0]);
        REXP resultMatrix = rEngine.eval(nameToAssignOn + " <- matrix( " + nameToAssignOn + " ,nr=1)");
        for (int i = 1; i < sourceArray.length; i++) {
            rEngine.assign("temp", sourceArray[i]);
            resultMatrix = rEngine.eval(nameToAssignOn + " <- rbind(" + nameToAssignOn + ",matrix(temp,nr=1))");
        }

        return resultMatrix;
    }
于 2014-04-13T16:39:00.607 に答える
2

参考までに(質問がされた時点ではまだ方法が利用できなかった可能性があります):

REXP REXP.createDoubleMatrix(double[][] arg);
于 2014-10-23T10:20:57.523 に答える
1

このようなことをした場合はどうなりますか(必要に応じて行番号と行番号を変更します)。

RConnection c = new RConnection();

double[][] test = { { 1.0D, 2.0D }, { 3.0D, 4.0D } };

c.assign("res", test[0]);
for (int i = 1; i < 2; i++) {
  c.assign("tmp", test[i]);
  c.eval("res<-rbind(res,tmp)");
}

REXP x = c.eval("sum(res)");
System.out.println(x.asString());

これは予想どおり10を返しますが、これは

String s = c.eval("rowSums(res)").asString();
System.out.println(s);

想定どおりに印刷されません。返されるだけ3です。UbuntuにインストールされたRServeが壊れていて、結果文字列のスペースの後にあるものを印刷できない可能性があります3 7

> rowSums(d)
c1 c2 
3  7 

そして私も良い例を見つけることができません:(

于 2012-10-27T07:04:32.050 に答える
0

あなたは出来る:

  • 配列を整数行のベクトルにフラット化します。

    a11 a12

    a21 a22

=>

flat_array = new int[] {a11, a12, a21, a22}
  • それをローカル変数に割り当てます。

    rEngine.assign(".values", flat_array);

  • 次のように、グローバルでマトリックス (またはデータフレーム) を作成する R 関数を呼び出します。

Rで:

 make.matrix <- function(nrows, ncols, values) {

        value_mat <- matrix(values, nrow=nrows, ncol=ncols, byrow=TRUE)
        temp.res <<- res
        res
    }

Java の場合:

rEngine.eval("make.matrix(2,2,.values)");
  • これで、temp.res にマトリックスができました
于 2014-05-15T00:49:15.983 に答える