Integrasi Java-R

1. Gambaran keseluruhan

R adalah bahasa pengaturcaraan yang popular digunakan untuk statistik. Oleh kerana ia mempunyai pelbagai fungsi dan pakej yang tersedia, ini bukan syarat biasa untuk memasukkan kod R ke dalam bahasa lain.

Dalam artikel ini, kita akan melihat beberapa cara yang paling biasa untuk mengintegrasikan kod R ke dalam Java.

2. Skrip R

Untuk projek kami, kami akan memulakan dengan menerapkan fungsi R yang sangat sederhana yang mengambil vektor sebagai input dan mengembalikan nilai nilainya. Kami akan menentukannya dalam fail khusus:

customMean <- function(vector) { mean(vector) }

Sepanjang tutorial ini, kami akan menggunakan kaedah Java helper untuk membaca fail ini dan mengembalikan kandungannya sebagai String :

String getMeanScriptContent() throws IOException, URISyntaxException { URI rScriptUri = RUtils.class.getClassLoader().getResource("script.R").toURI(); Path inputScript = Paths.get(rScriptUri); return Files.lines(inputScript).collect(Collectors.joining()); }

Sekarang, mari kita lihat pilihan yang berbeza yang harus kita gunakan untuk menggunakan fungsi ini dari Java.

3. RCaller

Perpustakaan pertama yang akan kita pertimbangkan adalah RCaller yang dapat menjalankan kod dengan melahirkan proses R khusus pada mesin tempatan.

Oleh kerana RCaller tersedia dari Maven Central, kami dapat memasukkannya ke dalam pom.xml kami :

 com.github.jbytecode RCaller 3.0 

Seterusnya, mari kita tulis kaedah khusus yang mengembalikan nilai rata-rata nilai kita dengan menggunakan skrip R asal kita:

public double mean(int[] values) throws IOException, URISyntaxException { String fileContent = RUtils.getMeanScriptContent(); RCode code = RCode.create(); code.addRCode(fileContent); code.addIntArray("input", values); code.addRCode("result <- customMean(input)"); RCaller caller = RCaller.create(code, RCallerOptions.create()); caller.runAndReturnResult("result"); return caller.getParser().getAsDoubleArray("result")[0]; }

Dalam kaedah ini kita menggunakan dua objek:

  • RCode , yang mewakili konteks kod kami, termasuk fungsi kami, inputnya, dan pernyataan permintaan
  • RCaller , yang membolehkan kami menjalankan kod kami dan mendapatkan hasilnya kembali

Penting untuk diperhatikan bahawa RCaller tidak sesuai untuk pengiraan kecil dan kerap kerana masa yang diperlukan untuk memulakan proses R. Ini adalah kelemahan yang ketara.

Juga, RCaller hanya berfungsi dengan R yang dipasang pada mesin tempatan .

4. Renjin

Renjin adalah satu lagi penyelesaian popular yang terdapat pada landskap integrasi R. Ia lebih banyak digunakan, dan juga menawarkan sokongan perusahaan .

Menambah Renjin ke projek kami agak remeh kerana kami harus menambahkan repositori bedatadriven bersama dengan pergantungan Maven:

  bedatadriven bedatadriven public repo //nexus.bedatadriven.com/content/groups/public/     org.renjin renjin-script-engine RELEASE  

Sekali lagi, mari buat pembungkus Java untuk fungsi R kami:

public double mean(int[] values) throws IOException, URISyntaxException, ScriptException { RenjinScriptEngine engine = new RenjinScriptEngine(); String meanScriptContent = RUtils.getMeanScriptContent(); engine.put("input", values); engine.eval(meanScriptContent); DoubleArrayVector result = (DoubleArrayVector) engine.eval("customMean(input)"); return result.asReal(); }

Seperti yang kita lihat, konsepnya sangat mirip dengan RCaller, walaupun kurang verbose , kerana kita dapat memanggil fungsi secara langsung dengan menggunakan nama menggunakan metode eval .

Kelebihan utama Renjin adalah bahawa ia tidak memerlukan pemasangan R kerana ia menggunakan jurubahasa berasaskan JVM. Walau bagaimanapun, Renjin pada masa ini tidak serasi 100% dengan GNU R.

5. Rserve

Perpustakaan yang kami kaji setakat ini adalah pilihan yang baik untuk menjalankan kod secara tempatan. Tetapi bagaimana jika kita ingin mempunyai banyak pelanggan yang menggunakan skrip R kita? Di situlah Rserve dimainkan, membiarkan kami menjalankan kod R pada mesin jauh melalui pelayan TCP .

Menyiapkan Rserve melibatkan pemasangan pakej yang berkaitan dan memulakan pelayan memuatkan skrip kami, melalui konsol R:

> install.packages("Rserve") ... > library("Rserve") > Rserve(args = "--RS-source ~/script.R") Starting Rserve...

Seterusnya, kita sekarang dapat memasukkan Rserve dalam projek kita dengan, seperti biasa, menambahkan kebergantungan Maven:

 org.rosuda.REngine Rserve 1.8.1 

Akhirnya, mari kita bungkus skrip R kita ke dalam kaedah Java. Di sini kita akan menggunakan objek RConnection dengan alamat pelayan kita, lalai ke 127.0.0.1:6311 jika tidak disediakan:

public double mean(int[] values) throws REngineException, REXPMismatchException { RConnection c = new RConnection(); c.assign("input", values); return c.eval("customMean(input)").asDouble(); }

6. FastR

Perpustakaan terakhir yang akan kita bincangkan ialah FastR. pelaksanaan R berprestasi tinggi yang dibina berdasarkan GraalVM. Pada masa penulisan ini, FastR hanya tersedia pada sistem Linux dan Darwin x64 .

Untuk menggunakannya, pertama-tama kita perlu memasang GraalVM dari laman web rasmi. Selepas itu, kita perlu memasang FastR sendiri menggunakan Graal Component Updater dan kemudian menjalankan skrip konfigurasi yang disertakan dengannya:

$ bin/gu install R ... $ languages/R/bin/configure_fastr

Kali ini kod kami akan bergantung pada Polyglot, API dalaman GraalVM untuk menanamkan bahasa tetamu yang berbeza di Java. Oleh kerana Polyglot adalah API umum, kami menentukan bahasa kod yang ingin kami jalankan. Juga, kami akan menggunakan fungsi c R untuk menukar input kami ke vektor:

public double mean(int[] values) { Context polyglot = Context.newBuilder().allowAllAccess(true).build(); String meanScriptContent = RUtils.getMeanScriptContent(); polyglot.eval("R", meanScriptContent); Value rBindings = polyglot.getBindings("R"); Value rInput = rBindings.getMember("c").execute(values); return rBindings.getMember("customMean").execute(rInput).asDouble(); }

Semasa mengikuti pendekatan ini, ingatlah bahawa ini menjadikan kod kami digabungkan dengan JVM . Untuk mengetahui lebih lanjut mengenai GraalVM, lihat artikel kami di Graal Java JIT Compiler.

7. Kesimpulannya

Dalam artikel ini, kami membahas beberapa teknologi yang paling popular untuk mengintegrasikan R di Java. Ringkasnya:

  • RCaller lebih mudah disatukan kerana ia tersedia di Maven Central
  • Renjin menawarkan sokongan perusahaan dan tidak memerlukan R dipasang pada mesin tempatan tetapi tidak serasi 100% dengan GNU R
  • Rserve dapat digunakan untuk menjalankan kod R pada pelayan jauh
  • FastR membolehkan integrasi lancar dengan Java tetapi membuat kod kami bergantung pada VM dan tidak tersedia untuk setiap OS

Seperti biasa, semua kod yang digunakan dalam tutorial ini terdapat di GitHub.