├── .gitignore ├── LICENSE ├── R └── rscala │ ├── .Rbuildignore │ ├── .gitignore │ ├── DESCRIPTION │ ├── LICENSE │ ├── NAMESPACE │ ├── NEWS │ ├── R │ ├── INTERNAL-callback.R │ ├── INTERNAL-checkConnection.R │ ├── INTERNAL-io.R │ ├── INTERNAL-pop.R │ ├── INTERNAL-protocol.R │ ├── INTERNAL-push.R │ ├── INTERNAL-r2scala.R │ ├── INTERNAL-rtypes.R │ ├── INTERNAL-scalaInvoke.R │ ├── close.R │ ├── dollar.R │ ├── dollarNames.R │ ├── is.scalaReference.R │ ├── ops.R │ ├── print.R │ ├── scala.R │ ├── scalaConfig.R │ ├── scalaDevelDeployJARs.R │ ├── scalaDisconnect.R │ ├── scalaFindBridge.R │ ├── scalaLast.R │ ├── scalaLazy.R │ ├── scalaMemory.R │ ├── scalaPull.R │ ├── scalaPush.R │ ├── scalaPushRegister.R │ ├── scalaSBT.R │ ├── scalaType.R │ ├── scalaVersionJARs.R │ ├── sysdata.rda │ └── zzz.R │ ├── README.md │ ├── inst │ ├── CITATION │ ├── COPYRIGHT │ ├── data-raw │ │ ├── sysdata │ │ └── urls.txt │ ├── doc │ │ ├── bootstrap-coverage.R │ │ ├── rscala.R │ │ ├── rscala.Rnw │ │ └── rscala.pdf │ ├── java │ │ ├── scala-2.11 │ │ │ └── rscala.jar │ │ ├── scala-2.12 │ │ │ └── rscala.jar │ │ └── scala-2.13 │ │ │ └── rscala.jar │ └── rstudio │ │ └── addins.dcf │ ├── java │ └── rscala-source.jar │ ├── man │ ├── close.rscalaBridge.Rd │ ├── is.scalaReference.Rd │ ├── plus-.rscalaBridge.Rd │ ├── pow-.rscalaBridge.Rd │ ├── scala.Rd │ ├── scalaConfig.Rd │ ├── scalaDevelDeployJARs.Rd │ ├── scalaDisconnect.Rd │ ├── scalaFindBridge.Rd │ ├── scalaLast.Rd │ ├── scalaLazy.Rd │ ├── scalaMemory.Rd │ ├── scalaPush.Rd │ ├── scalaPushRegister.Rd │ ├── scalaSBT.Rd │ ├── scalaType.Rd │ ├── scalaVersionJARs.Rd │ └── times-.rscalaBridge.Rd │ ├── rscala.Rproj │ ├── tests │ ├── testthat.R │ └── testthat │ │ ├── setup-instance.R │ │ ├── teardown-instance.R │ │ ├── tests-callbacks.R │ │ ├── tests-dollar.R │ │ ├── tests-lexical-scoping.R │ │ ├── tests-matrices.R │ │ ├── tests-object-serialization.R │ │ ├── tests-output-serialization.R │ │ ├── tests-recursion.R │ │ ├── tests-transcompile.R │ │ └── tests-vectors.R │ └── vignettes │ ├── .install_extras │ ├── bootstrap-coverage.R │ ├── build-vignette │ ├── jss.bst │ ├── jss.cls │ ├── rscala.Rnw │ └── rscala.bib ├── README.md ├── benchmarks ├── all ├── benchmark-compile-rscala_2.5.3.R ├── benchmark-compile-rscala_2.5.3.Rout ├── benchmark-compile.R ├── benchmark-compile.Rout ├── benchmark-invocation-rscala_2.5.3.R ├── benchmark-invocation-rscala_2.5.3.Rout ├── benchmark-invocation.R ├── benchmark-invocation.Rout ├── benchmark-large-rscala_2.5.3.R ├── benchmark-large-rscala_2.5.3.Rout ├── benchmark-large.R ├── benchmark-large.Rout ├── benchmark-references-rscala_2.5.3.R ├── benchmark-references-rscala_2.5.3.Rout ├── benchmark-references.R └── benchmark-references.Rout ├── bin ├── check ├── make-protocol ├── package ├── post ├── scrape-CRAN-check ├── setup-remotes ├── shortcut └── tag ├── build.sbt ├── deliveries ├── rscalaJars_2.3.1.tar.gz ├── rscalaJars_2.3.2.tar.gz ├── rscalaJars_2.3.3.tar.gz ├── rscalaJars_2.3.4.tar.gz ├── rscalaJars_2.3.5.tar.gz ├── rscalaJars_2.4.0.tar.gz ├── rscalaJars_2.5.0.tar.gz ├── rscalaJars_2.5.1.tar.gz ├── rscalaJars_2.5.2.tar.gz ├── rscalaJars_2.5.3.tar.gz ├── rscala_1.0.0.tar.gz ├── rscala_1.0.1.tar.gz ├── rscala_1.0.10.tar.gz ├── rscala_1.0.11.tar.gz ├── rscala_1.0.12.tar.gz ├── rscala_1.0.13.tar.gz ├── rscala_1.0.14.tar.gz ├── rscala_1.0.2.tar.gz ├── rscala_1.0.3.tar.gz ├── rscala_1.0.4.tar.gz ├── rscala_1.0.5.tar.gz ├── rscala_1.0.6.tar.gz ├── rscala_1.0.7.tar.gz ├── rscala_1.0.8.tar.gz ├── rscala_1.0.9.tar.gz ├── rscala_2.0.0.tar.gz ├── rscala_2.0.1.tar.gz ├── rscala_2.1.0.tar.gz ├── rscala_2.1.1.tar.gz ├── rscala_2.2.0.tar.gz ├── rscala_2.2.1.tar.gz ├── rscala_2.2.2.tar.gz ├── rscala_2.3.1.tar.gz ├── rscala_2.3.2.tar.gz ├── rscala_2.3.3.tar.gz ├── rscala_2.3.4.tar.gz ├── rscala_2.3.5.tar.gz ├── rscala_2.4.0.tar.gz ├── rscala_2.5.0.tar.gz ├── rscala_2.5.1.tar.gz ├── rscala_2.5.2.tar.gz ├── rscala_2.5.3.tar.gz ├── rscala_3.0.0.tar.gz ├── rscala_3.0.1.tar.gz ├── rscala_3.0.2.tar.gz ├── rscala_3.1.0.tar.gz ├── rscala_3.2.0.tar.gz ├── rscala_3.2.1.tar.gz ├── rscala_3.2.10.tar.gz ├── rscala_3.2.11.tar.gz ├── rscala_3.2.12.tar.gz ├── rscala_3.2.13.tar.gz ├── rscala_3.2.14.tar.gz ├── rscala_3.2.15.tar.gz ├── rscala_3.2.16.tar.gz ├── rscala_3.2.17.tar.gz ├── rscala_3.2.18.tar.gz ├── rscala_3.2.19.tar.gz ├── rscala_3.2.2.tar.gz ├── rscala_3.2.21.tar.gz ├── rscala_3.2.3.tar.gz ├── rscala_3.2.4.tar.gz ├── rscala_3.2.5.tar.gz ├── rscala_3.2.6.tar.gz ├── rscala_3.2.7.tar.gz ├── rscala_3.2.8.tar.gz └── rscala_3.2.9.tar.gz ├── examples ├── callRfromScala-usingPackageJAR ├── callRfromScala │ ├── .gitignore │ ├── CallRFromScala.scala │ ├── build.sbt │ ├── project │ │ └── build.properties │ └── run ├── root-finding.R └── root-finding.Rout ├── others └── hanyu-song │ ├── parallel-package.pdf │ ├── psm_ex.RData │ ├── salso_parallel_ex-DBD.R │ └── salso_parallel_ex.R ├── project ├── build.properties └── plugins.sbt ├── release-procedure ├── reverse-dependencies ├── .gitignore ├── check ├── list └── packages │ ├── bamboo_0.9.23.tar.gz │ ├── commonsMath_1.2.tar.gz │ ├── sdols_1.7.tar.gz │ └── shallot_0.4.5.tar.gz ├── scratch ├── .keep ├── scratch.R ├── testing └── todo.txt └── src └── main ├── scala-2.11 └── org │ └── ddahl │ └── rscala │ └── server │ ├── ServerStub.scala │ └── TranscompileStub.scala ├── scala-2.12 └── org │ └── ddahl │ └── rscala │ └── server │ ├── ServerStub.scala │ └── TranscompileStub.scala ├── scala-2.13 └── org │ └── ddahl │ └── rscala │ └── server │ ├── ServerStub.scala │ └── TranscompileStub.scala └── scala └── org └── ddahl └── rscala ├── RClient.scala └── server ├── Conduit.scala ├── Datum.scala ├── Debugger.scala ├── Main.scala ├── Protocol.scala ├── Server.scala ├── Sockets.scala └── Transcompile.scala /.gitignore: -------------------------------------------------------------------------------- 1 | /target 2 | /project/target 3 | /project/project/target 4 | /R/rscala_*.tar.gz 5 | /R/rscala.Rcheck 6 | /R/rscala/vignettes/rscala.aux 7 | /R/rscala/vignettes/rscala.bbl 8 | /R/rscala/vignettes/rscala.blg 9 | /R/rscala/vignettes/rscala.log 10 | /R/rscala/vignettes/rscala.out 11 | /R/rscala/vignettes/rscala.pdf 12 | /R/rscala/vignettes/rscala.tex 13 | /R/rscala/vignettes/rscala-concordance.tex 14 | /R/rscala/vignettes/rscala.synctex.gz 15 | /src/main/resources 16 | /deliveries/rscala_*.tar.gz 17 | /deliveries/rscala*.Rcheck 18 | /deliveries/rscala.pdf 19 | .Rhistory 20 | .RData 21 | /others 22 | /cran-check-results 23 | 24 | # User-specific stuff: 25 | /.idea 26 | /.idea/workspace.xml 27 | /.idea/tasks.xml 28 | /.idea/dictionaries 29 | /.idea/vcs.xml 30 | /.idea/jsLibraryMappings.xml 31 | 32 | # Sensitive or high-churn files: 33 | /.idea/dataSources.ids 34 | /.idea/dataSources.xml 35 | /.idea/dataSources.local.xml 36 | /.idea/sqlDataSources.xml 37 | /.idea/dynamic.xml 38 | /.idea/uiDesigner.xml 39 | 40 | .Rproj.user 41 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | Licensing information is contained in: 2 | 3 | build.sbt 4 | R/rscala/DESCRIPTION 5 | R/rscala/LICENSE 6 | 7 | -------------------------------------------------------------------------------- /R/rscala/.Rbuildignore: -------------------------------------------------------------------------------- 1 | ^.*\.Rproj$ 2 | ^\.Rproj\.user$ 3 | jss\.cls$ 4 | jss\.bst$ 5 | rscala.bbl$ 6 | rscala.blg$ 7 | build-vignette$ 8 | ^doc$ 9 | ^Meta$ 10 | -------------------------------------------------------------------------------- /R/rscala/.gitignore: -------------------------------------------------------------------------------- 1 | /doc/ 2 | /Meta/ 3 | -------------------------------------------------------------------------------- /R/rscala/DESCRIPTION: -------------------------------------------------------------------------------- 1 | Package: rscala 2 | Type: Package 3 | Title: Bridge Between 'R' and 'Scala' with Callbacks 4 | Version: 3.2.26 5 | Authors@R: person(given="David B.",family="Dahl",role=c("aut","cre"),email="dahl@stat.byu.edu") 6 | URL: https://github.com/dbdahl/rscala 7 | BugReports: https://github.com/dbdahl/rscala/issues 8 | Imports: utils 9 | SystemRequirements: Scala (>= 2.11), Java (>= 8) 10 | Description: 'Scala' is embedded in 'R' and callbacks from 'Scala' to 'R' are available. Support is provided to write 'R' packages that access 'Scala'. After installation, please run 'rscala::scalaConfig()'. The vignette provides an update of the original paper . 11 | Depends: R (>= 3.1.0) 12 | License: Apache License 2.0 | file LICENSE 13 | Encoding: UTF-8 14 | RoxygenNote: 7.2.3 15 | Suggests: knitr, testthat, devtools, rstudioapi, processx 16 | VignetteBuilder: knitr 17 | -------------------------------------------------------------------------------- /R/rscala/NAMESPACE: -------------------------------------------------------------------------------- 1 | # Generated by roxygen2: do not edit by hand 2 | 3 | S3method("$",rscalaBridge) 4 | S3method("$",rscalaReference) 5 | S3method("$<-",rscalaBridge) 6 | S3method("*",rscalaBridge) 7 | S3method("+",rscalaBridge) 8 | S3method("^",rscalaBridge) 9 | S3method(.DollarNames,rscalaReference) 10 | S3method(close,rscalaBridge) 11 | S3method(print,rscalaBridge) 12 | S3method(print,rscalaReference) 13 | S3method(print,rscalaSub) 14 | S3method(print,rscalaType) 15 | S3method(toString,rscalaBridge) 16 | S3method(toString,rscalaReference) 17 | S3method(toString,rscalaSub) 18 | S3method(toString,rscalaType) 19 | export(is.scalaReference) 20 | export(scala) 21 | export(scalaConfig) 22 | export(scalaDevelDeployJARs) 23 | export(scalaDisconnect) 24 | export(scalaFindBridge) 25 | export(scalaLast) 26 | export(scalaLazy) 27 | export(scalaMemory) 28 | export(scalaPull) 29 | export(scalaPullRegister) 30 | export(scalaPush) 31 | export(scalaPushRegister) 32 | export(scalaSBT) 33 | export(scalaType) 34 | export(scalaVersionJARs) 35 | export(stD0) 36 | export(stD1) 37 | export(stD2) 38 | export(stI0) 39 | export(stI1) 40 | export(stI2) 41 | export(stL0) 42 | export(stL1) 43 | export(stL2) 44 | export(stR0) 45 | export(stR1) 46 | export(stR2) 47 | export(stS0) 48 | export(stS1) 49 | export(stS2) 50 | importFrom(tools,dependsOnPkgs) 51 | importFrom(tools,md5sum) 52 | importFrom(utils,.DollarNames) 53 | importFrom(utils,compareVersion) 54 | importFrom(utils,download.file) 55 | importFrom(utils,getFromNamespace) 56 | -------------------------------------------------------------------------------- /R/rscala/R/INTERNAL-callback.R: -------------------------------------------------------------------------------- 1 | callback <- function(details, envir) { 2 | socketIn <- details[["socketIn"]] 3 | snippet <- rc(socketIn) 4 | nArgs <- rb(socketIn,RTYPE_INT) 5 | args <- vector(mode="list", length=nArgs) 6 | while ( TRUE ) { 7 | argsListName <- paste0(".rs",sample.int(.Machine$integer.max,1L)) 8 | if ( ! exists(argsListName,envir=envir) ) break 9 | } 10 | for ( i in seq_len(nArgs) ) { 11 | arg <- pop(details) 12 | rhs <- paste0(argsListName,"[[",i,"]]") 13 | if ( is.list(arg) ) { 14 | arg <- arg[['value']] 15 | rhs <- paste0("unserialize(",rhs,")") 16 | } 17 | snippet <- sub("%-",rhs,snippet) 18 | args[[i]] <- arg 19 | } 20 | assign(argsListName,args,envir=envir) 21 | result <- tryCatch(eval(parse(text=snippet),envir=envir), error=function(e) { 22 | cat(toString(e)) 23 | NULL 24 | }) 25 | rm(list=argsListName,envir=envir) 26 | socketOut <- details[["socketOut"]] 27 | wb(socketOut, PCODE_REXIT) 28 | pushOkay <- push(result, NULL, socketOut) 29 | if ( ! identical(pushOkay,TRUE) ) { 30 | cat(attr(pushOkay,"msg"),"\n",sep="") 31 | push(NULL, NULL, socketOut) 32 | } 33 | } 34 | -------------------------------------------------------------------------------- /R/rscala/R/INTERNAL-checkConnection.R: -------------------------------------------------------------------------------- 1 | checkConnection <- function(details) { 2 | if ( Sys.getpid() != details[["pidOfR"]] ) { 3 | close.rscalaBridge(details) 4 | stop("Each process should have its own Scala bridge. Closing this bridge.") 5 | } 6 | if ( details[['closed']] ) stop("Bridge is closed.") 7 | } 8 | -------------------------------------------------------------------------------- /R/rscala/R/INTERNAL-io.R: -------------------------------------------------------------------------------- 1 | wb <- function(con,x) { 2 | writeBin(x,con,endian="big") 3 | } 4 | 5 | wc <- function(con,x) { 6 | bytes <- charToRaw(iconv(x,to="UTF-8")) 7 | writeBin(length(bytes),con,endian="big") 8 | writeBin(bytes,con,endian="big") 9 | } 10 | 11 | rbyte <- function(con) { 12 | counter <- 0L 13 | while ( TRUE ) { 14 | x <- tryCatch({ 15 | readBin(con,RTYPE_RAW,endian="big") 16 | },interrupt=function(e) { 17 | TCODE_INTERRUPTED 18 | }) 19 | if ( length(x) > 0 ) return(x) 20 | counter <- counter + 1L 21 | if ( ( counter %% 100L == 0L ) && ( scalaIsDead(con) ) ) stop("Scala seems to have died.") 22 | } 23 | } 24 | 25 | rc <- function(con) { 26 | len <- rb(con,RTYPE_INT) 27 | r <- rb(con,RTYPE_RAW,len) 28 | iconv(rawToChar(r),from="UTF-8") 29 | } 30 | 31 | rb <- function(con,v,n=1L) { 32 | tryCatch({ 33 | r <- readBin(con,v,n,endian="big") 34 | if ( length(r) == n ) r 35 | else { 36 | counter <- 0L 37 | while ( length(r) != n ) { 38 | counter <- counter + 1L 39 | if ( ( counter %% 100L == 0L ) && ( scalaIsDead(con) ) ) stop("Scala seems to have died.") 40 | r <- c(r,readBin(con,v,n-length(r),endian="big")) 41 | } 42 | r 43 | } 44 | },error=function(e) { 45 | stop("The bridge is invalid.") 46 | }) 47 | } 48 | 49 | scalaIsDead <- function(con) { 50 | pidOfScala <- attr(con,"pidOfScala") 51 | if ( is.null(pidOfScala) ) return(TRUE) 52 | if ( .Platform$OS.type == "unix" ) { 53 | tryCatch(length(system2("ps",c("-o","pid=","-p",pidOfScala),stdout=TRUE)) == 0, 54 | warning=function(e) TRUE, error=function(e) TRUE) 55 | } else if ( .Platform$OS.type == "windows" ) { 56 | tryCatch(length(system2("tasklist",c("/fo","csv","/fi",sprintf('"PID eq %s"',pidOfScala)),stdout=TRUE)) == 1, 57 | warning=function(e) TRUE, error=function(e) TRUE) 58 | } else stop("Unsupported OS.") 59 | } 60 | 61 | -------------------------------------------------------------------------------- /R/rscala/R/INTERNAL-pop.R: -------------------------------------------------------------------------------- 1 | pop <- function(details, transcompileInfo=NULL, envir=NULL) { 2 | socketIn <- details[["socketIn"]] 3 | serializeOutput <- details[["serializeOutput"]] 4 | goAgain <- TRUE 5 | while ( goAgain ) { 6 | goAgain <- FALSE 7 | if ( serializeOutput ) cat(rc(socketIn)) 8 | tipe <- rbyte(socketIn) 9 | result <- if ( tipe == TCODE_INT_0 ) { 10 | rb(socketIn,RTYPE_INT) 11 | } else if ( tipe == TCODE_INT_1 ) { 12 | len <- rb(socketIn,RTYPE_INT) 13 | rb(socketIn,RTYPE_INT,len) 14 | } else if ( tipe == TCODE_INT_2 ) { 15 | dim <- rb(socketIn,RTYPE_INT,2L) 16 | matrix(rb(socketIn,RTYPE_INT,prod(dim)),nrow=dim[1],byrow=TRUE) 17 | } else if ( tipe == TCODE_DOUBLE_0 ) { 18 | rb(socketIn,RTYPE_DOUBLE) 19 | } else if ( tipe == TCODE_DOUBLE_1 ) { 20 | len <- rb(socketIn,RTYPE_INT) 21 | rb(socketIn,RTYPE_DOUBLE,len) 22 | } else if ( tipe == TCODE_DOUBLE_2 ) { 23 | dim <- rb(socketIn,RTYPE_INT,2L) 24 | matrix(rb(socketIn,RTYPE_DOUBLE,prod(dim)),nrow=dim[1],byrow=TRUE) 25 | } else if ( tipe == TCODE_LOGICAL_0 ) { 26 | as.logical(rb(socketIn,RTYPE_RAW)) 27 | } else if ( tipe == TCODE_LOGICAL_1 ) { 28 | len <- rb(socketIn,RTYPE_INT) 29 | as.logical(rb(socketIn,RTYPE_RAW,len)) 30 | } else if ( tipe == TCODE_LOGICAL_2 ) { 31 | dim <- rb(socketIn,RTYPE_INT,2L) 32 | matrix(as.logical(rb(socketIn,RTYPE_RAW,prod(dim))),nrow=dim[1],byrow=TRUE) 33 | } else if ( tipe == TCODE_RAW_0 ) { 34 | rb(socketIn,RTYPE_RAW) 35 | } else if ( tipe == TCODE_RAW_1 ) { 36 | len <- rb(socketIn,RTYPE_INT) 37 | rb(socketIn,RTYPE_RAW,len) 38 | } else if ( tipe == TCODE_ROBJECT ) { 39 | len <- rb(socketIn,RTYPE_INT) 40 | list(value=rb(socketIn,RTYPE_RAW,len)) 41 | } else if ( tipe == TCODE_RAW_2 ) { 42 | dim <- rb(socketIn,RTYPE_INT,2L) 43 | matrix(rb(socketIn,RTYPE_RAW,prod(dim)),nrow=dim[1],byrow=TRUE) 44 | } else if ( tipe == TCODE_CHARACTER_0 ) { 45 | rc(socketIn) 46 | } else if ( tipe == TCODE_CHARACTER_1 ) { 47 | len <- rb(socketIn,RTYPE_INT) 48 | result <- character(len) 49 | for ( i in seq_len(len) ) result[i] <- rc(socketIn) 50 | result 51 | } else if ( tipe == TCODE_CHARACTER_2 ) { 52 | dim <- rb(socketIn,RTYPE_INT,2L) 53 | result <- matrix(character(prod(dim)),nrow=dim[1]) 54 | for ( i in seq_len(dim[1]) ) for ( j in seq_len(dim[2]) ) result[i,j] <- rc(socketIn) 55 | result 56 | } else if ( tipe == TCODE_UNIT ) { 57 | invisible() 58 | } else if ( tipe == TCODE_REFERENCE ) { 59 | referenceID <- rb(socketIn,RTYPE_INT) 60 | referenceType <- rc(socketIn) 61 | func <- if ( is.null(transcompileInfo) ) { 62 | function(...) { 63 | scalaInvoke(details, "apply", list(..., env), envir, withReference=TRUE) 64 | } 65 | } else { 66 | function(...) { 67 | args <- list(...) 68 | types <- transcompileInfo$argTypes 69 | for ( i in seq_along(args) ) { 70 | args[[i]] <- if ( types[i] == "Double" ) as.double(args[[i]][1]) 71 | else if ( types[i] == "Int" ) as.integer(args[[i]][1]) 72 | else if ( types[i] == "Boolean" ) as.logical(args[[i]][1]) 73 | else if ( types[i] == "String" ) as.character(args[[i]][1]) 74 | else if ( types[i] == "Array[Double]" ) I(as.double(args[[i]])) 75 | else if ( types[i] == "Array[Int]" ) I(as.integer(args[[i]])) 76 | else if ( types[i] == "Array[Boolean]" ) I(as.logical(args[[i]])) 77 | else if ( types[i] == "Array[String]" ) I(as.character(args[[i]])) 78 | else args[[i]] 79 | } 80 | scalaInvoke(details, "apply", c(args, env), envir, withReference=TRUE) 81 | } 82 | } 83 | class(func) <- "rscalaReference" 84 | env <- structure(list2env(list(id=referenceID,type=referenceType,details=details,original=transcompileInfo$original,envir=envir),parent=emptyenv()), class="rscalaReferenceEnvironment") 85 | reg.finalizer(env, details[["gcFunction"]]) 86 | attr(func,"rscalaReferenceEnvironment") <- env 87 | func 88 | } else if ( tipe == TCODE_ERROR_DEF ) { 89 | code <- rc(socketIn) 90 | stop(paste0("Compilation error. Code is:\n",code)) 91 | } else if ( tipe == TCODE_ERROR_INVOKE ) { 92 | stop("Invocation error.") 93 | } else if ( tipe == TCODE_INTERRUPTED ) { 94 | cat("<< computation interrupted >>\n") 95 | assign("interrupted",TRUE,envir=details) 96 | return(invisible()) 97 | } else if ( tipe == TCODE_CALLBACK ) { 98 | callback(details, envir) 99 | goAgain <- TRUE 100 | } else stop(paste0("Unsupported type: ",tipe)) 101 | } 102 | assign("last",result,envir=details) 103 | if ( is.null(result) ) invisible() else result 104 | } 105 | -------------------------------------------------------------------------------- /R/rscala/R/INTERNAL-protocol.R: -------------------------------------------------------------------------------- 1 | PCODE_SHUTDOWN <- as.raw(10) 2 | PCODE_REXIT <- as.raw(11) 3 | PCODE_PUSH_WITH_NAME <- as.raw(12) 4 | PCODE_PUSH_WITHOUT_NAME <- as.raw(13) 5 | PCODE_CLEAR <- as.raw(14) 6 | PCODE_INVOKE <- as.raw(15) 7 | PCODE_INVOKE_WITH_REFERENCE <- as.raw(16) 8 | PCODE_INVOKE_FREEFORM <- as.raw(17) 9 | PCODE_GARBAGE_COLLECT <- as.raw(18) 10 | PCODE_SUSPEND <- as.raw(19) 11 | TCODE_INT_0 <- as.raw(50) 12 | TCODE_INT_1 <- as.raw(51) 13 | TCODE_INT_2 <- as.raw(52) 14 | TCODE_DOUBLE_0 <- as.raw(53) 15 | TCODE_DOUBLE_1 <- as.raw(54) 16 | TCODE_DOUBLE_2 <- as.raw(55) 17 | TCODE_LOGICAL_0 <- as.raw(56) 18 | TCODE_LOGICAL_1 <- as.raw(57) 19 | TCODE_LOGICAL_2 <- as.raw(58) 20 | TCODE_RAW_0 <- as.raw(59) 21 | TCODE_RAW_1 <- as.raw(60) 22 | TCODE_RAW_2 <- as.raw(61) 23 | TCODE_CHARACTER_0 <- as.raw(62) 24 | TCODE_CHARACTER_1 <- as.raw(63) 25 | TCODE_CHARACTER_2 <- as.raw(64) 26 | TCODE_UNIT <- as.raw(65) 27 | TCODE_REFERENCE <- as.raw(70) 28 | TCODE_ROBJECT <- as.raw(71) 29 | TCODE_ERROR_DEF <- as.raw(80) 30 | TCODE_ERROR_INVOKE <- as.raw(81) 31 | TCODE_INTERRUPTED <- as.raw(82) 32 | TCODE_CALLBACK <- as.raw(90) 33 | -------------------------------------------------------------------------------- /R/rscala/R/INTERNAL-push.R: -------------------------------------------------------------------------------- 1 | MAXIMUM_RAW_LENGTH <- 2147483647L - 5L 2 | 3 | push <- function(what, name, socketOut) { 4 | pcode <- if ( is.null(name) ) PCODE_PUSH_WITHOUT_NAME 5 | else PCODE_PUSH_WITH_NAME 6 | forceVector <- if ( inherits(what,"AsIs") ) { 7 | what <- unclass(what) 8 | TRUE 9 | } else FALSE 10 | if ( inherits(what, "rscalaReferenceEnvironment") ) { 11 | wb(socketOut,c(pcode,TCODE_REFERENCE)) 12 | wb(socketOut,what[["id"]]) 13 | } else if ( inherits(what, "rscalaReference") ) { 14 | wb(socketOut,c(pcode,TCODE_REFERENCE)) 15 | wb(socketOut,attr(what,"rscalaReferenceEnvironment")[["id"]]) 16 | } else if ( is.integer(what) ) { 17 | if ( length(what)*4 > MAXIMUM_RAW_LENGTH ) return(structure(FALSE,msg="Object exceeds maximum supported length.")) 18 | if ( is.matrix(what) ) { 19 | dim <- dim(what) 20 | if ( dim[1] == 0L ) return(structure(FALSE,msg="Number of rows must be at least 1.")) 21 | wb(socketOut,c(pcode,TCODE_INT_2)) 22 | wb(socketOut,dim) 23 | what <- t(what) 24 | attr(what,"dim") <- NULL 25 | wb(socketOut,what) 26 | } else if ( ( ! forceVector ) && ( length(what) == 1L ) ) { 27 | wb(socketOut,c(pcode,TCODE_INT_0)) 28 | wb(socketOut,what) 29 | } else { 30 | wb(socketOut,c(pcode,TCODE_INT_1)) 31 | wb(socketOut,c(length(what),what)) 32 | } 33 | } else if ( is.double(what) ) { 34 | if ( length(what)*8 > MAXIMUM_RAW_LENGTH ) return(structure(FALSE,msg="Object exceeds maximum supported length.")) 35 | if ( is.matrix(what) ) { 36 | dim <- dim(what) 37 | if ( dim[1] == 0L ) return(structure(FALSE,msg="Number of rows must be at least 1.")) 38 | wb(socketOut,c(pcode,TCODE_DOUBLE_2)) 39 | wb(socketOut,dim) 40 | what <- t(what) 41 | attr(what,"dim") <- NULL 42 | wb(socketOut,what) 43 | } else if ( ( ! forceVector ) && ( length(what) == 1L ) ) { 44 | wb(socketOut,c(pcode,TCODE_DOUBLE_0)) 45 | wb(socketOut,what) 46 | } else { 47 | wb(socketOut,c(pcode,TCODE_DOUBLE_1)) 48 | wb(socketOut,length(what)) 49 | wb(socketOut,what) 50 | } 51 | } else if ( is.logical(what) ) { 52 | if ( length(what) > MAXIMUM_RAW_LENGTH ) return(structure(FALSE,msg="Object exceeds maximum supported length.")) 53 | if ( is.matrix(what) ) { 54 | dim <- dim(what) 55 | if ( dim[1] == 0L ) return(structure(FALSE,msg="Number of rows must be at least 1.")) 56 | wb(socketOut,c(pcode,TCODE_LOGICAL_2)) 57 | wb(socketOut,dim) 58 | what <- t(what) 59 | attr(what,"dim") <- NULL 60 | wb(socketOut,as.raw(what)) 61 | } else if ( ( ! forceVector ) && ( length(what) == 1L ) ) { 62 | wb(socketOut,c(pcode,TCODE_LOGICAL_0)) 63 | wb(socketOut,as.raw(what)) 64 | } else { 65 | wb(socketOut,c(pcode,TCODE_LOGICAL_1)) 66 | wb(socketOut,length(what)) 67 | wb(socketOut,as.raw(what)) 68 | } 69 | } else if ( is.raw(what) ) { 70 | if ( length(what) > MAXIMUM_RAW_LENGTH ) return(structure(FALSE,msg="Object exceeds maximum supported length.")) 71 | if ( is.matrix(what) ) { 72 | dim <- dim(what) 73 | if ( dim[1] == 0L ) return(structure(FALSE,msg="Number of rows must be at least 1.")) 74 | wb(socketOut,c(pcode,TCODE_RAW_2)) 75 | wb(socketOut,dim) 76 | what <- t(what) 77 | attr(what,"dim") <- NULL 78 | wb(socketOut,what) 79 | } else if ( ( ! forceVector ) && ( length(what) == 1L ) ) { 80 | wb(socketOut,c(pcode,TCODE_RAW_0)) 81 | wb(socketOut,what) 82 | } else { 83 | wb(socketOut,c(pcode,TCODE_RAW_1)) 84 | wb(socketOut,length(what)) 85 | wb(socketOut,what) 86 | } 87 | } else if ( is.character(what) ) { 88 | if ( is.matrix(what) ) { 89 | dim <- dim(what) 90 | if ( dim[1] == 0L ) return(structure(FALSE,msg="Number of rows must be at least 1.")) 91 | wb(socketOut,c(pcode,TCODE_CHARACTER_2)) 92 | wb(socketOut,dim) 93 | what <- t(what) 94 | attr(what,"dim") <- NULL 95 | sapply(what, function(x) wc(socketOut,x)) 96 | } else if ( ( ! forceVector ) && ( length(what) == 1L ) ) { 97 | wb(socketOut,c(pcode,TCODE_CHARACTER_0)) 98 | wc(socketOut,what) 99 | } else { 100 | wb(socketOut,c(pcode,TCODE_CHARACTER_1)) 101 | wb(socketOut,length(what)) 102 | sapply(what, function(x) wc(socketOut,x)) 103 | } 104 | } else if ( is.null(what) ) { 105 | wb(socketOut,c(pcode,TCODE_UNIT)) 106 | } else return(structure(FALSE,msg=paste0("Unsupported type: ",class(what)))) 107 | if ( ! is.null(name) ) wc(socketOut,name) 108 | TRUE 109 | } 110 | -------------------------------------------------------------------------------- /R/rscala/R/INTERNAL-rtypes.R: -------------------------------------------------------------------------------- 1 | RTYPE_INT <- integer() 2 | RTYPE_DOUBLE <- double() 3 | RTYPE_LOGICAL <- logical() 4 | RTYPE_RAW <- raw() 5 | -------------------------------------------------------------------------------- /R/rscala/R/INTERNAL-scalaInvoke.R: -------------------------------------------------------------------------------- 1 | scalaInvoke <- function(details, snippet, args, envir, withNames=FALSE, withReference=FALSE, transcompileInfo=NULL) { 2 | if ( ( ! is.vector(snippet) ) || ( length(snippet) != 1 ) ) stop("'snippet' should be a character vector of length one.") 3 | if ( details[["disconnected"]] ) scalaConnect(details) 4 | scalaLastEngine(details) 5 | if ( details[["interrupted"]] ) return(invisible()) 6 | socketOut <- details[["socketOut"]] 7 | if ( length(details[["garbage"]]) > 0 ) { 8 | # Careful! R's garbage collector can mutate 'details[["garbage"]]'. 9 | wb(socketOut,PCODE_GARBAGE_COLLECT) 10 | what <- details[["garbage"]] 11 | wb(socketOut,c(length(what),what)) 12 | details[["garbage"]] <- setdiff(details[["garbage"]],what) 13 | } 14 | args <- rev(args) 15 | names <- names(args) 16 | for ( i in seq_along(args) ) { 17 | result <- push(args[[i]], names[i], socketOut) 18 | if ( ! identical(result,TRUE) ) { 19 | if ( i > 1 ) { 20 | wb(socketOut,PCODE_CLEAR) 21 | wb(socketOut,as.integer(i-1L)) 22 | } 23 | stop(attr(result,"msg")) 24 | } 25 | } 26 | if ( withReference ) { 27 | wb(socketOut,PCODE_INVOKE_WITH_REFERENCE) 28 | } else { 29 | if ( withNames ) wb(socketOut,PCODE_INVOKE_FREEFORM) 30 | else wb(socketOut,PCODE_INVOKE) 31 | } 32 | len <- if ( is.null(args) ) -1L else length(args) 33 | wb(socketOut,len) 34 | wc(socketOut,snippet) 35 | pop(details, transcompileInfo, envir) 36 | } 37 | -------------------------------------------------------------------------------- /R/rscala/R/close.R: -------------------------------------------------------------------------------- 1 | #' Close a Scala Bridge 2 | #' 3 | #' @param con A Scala bridge. 4 | #' @param ... Currently ignored. 5 | #' 6 | #' @return Returns \code{NULL}, invisibly. 7 | #' @export 8 | #' 9 | close.rscalaBridge <- function(con, ...) { 10 | details <- if ( inherits(con,"rscalaBridge") ) attr(con,"details") else con 11 | if ( details[["closed"]] ) return(invisible()) 12 | assign("closed",TRUE,envir=details) 13 | unlink(details[["sessionFilename"]]) 14 | if ( identical(.Platform$OS.type,"windows") && ( ! interactive() ) ) { 15 | Sys.sleep(15) 16 | } 17 | if ( ! details[["disconnected"]] ) { 18 | tryCatch( close(details[["socketIn"]] ), error=function(e) NULL ) 19 | tryCatch( close(details[["socketOut"]] ), error=function(e) NULL ) 20 | } 21 | invisible() 22 | } 23 | 24 | -------------------------------------------------------------------------------- /R/rscala/R/dollar.R: -------------------------------------------------------------------------------- 1 | #' @export 2 | #' 3 | "$.rscalaBridge" <- function(bridge, snippet) { 4 | if ( ! is.function(bridge) ) stop("When defining an rscala function, parameter lists are not supported.") 5 | details <- attr(bridge,"details") 6 | structure(function(...) { 7 | scalaInvoke(details, snippet, list(...), parent.frame(1)) 8 | },class="rscalaStub") 9 | } 10 | 11 | #' @export 12 | #' 13 | "$.rscalaReference" <- function(reference, snippet) { 14 | rre <- attr(reference,"rscalaReferenceEnvironment") 15 | details <- rre[["details"]] 16 | envir <- rre[["envir"]] 17 | structure(function(...) { 18 | scalaInvoke(details, snippet, list(...,reference), envir, withReference=TRUE) 19 | },class="rscalaStub") 20 | } 21 | 22 | #' @export 23 | #' 24 | "$<-.rscalaBridge" <- function(bridge, snippet, value) { 25 | details <- attr(bridge,"details") 26 | if ( snippet == "showCode" ) { 27 | bridge(x=as.logical(value[1])) ^ "conduit.showCode = x" 28 | } else if ( snippet == "debugTranscompilation" ) { 29 | assign("debugTranscompilation",identical(value,TRUE),envir=details) 30 | } else if ( snippet == "debug" ) { 31 | bridge(x=as.logical(value[1])) ^ "conduit.debug = x" 32 | } else stop(paste0("Unsupported option: ", snippet)) 33 | bridge 34 | } 35 | -------------------------------------------------------------------------------- /R/rscala/R/dollarNames.R: -------------------------------------------------------------------------------- 1 | #' @export 2 | #' @importFrom utils .DollarNames 3 | #' 4 | .DollarNames.rscalaReference <- function(x, pattern="") { 5 | # There is a bug that crashes the traditional Windows GUI. Just bug-out in that case. 6 | if ( ( .Platform$OS.type == "windows" ) && ( .Platform$GUI != "RStudio" ) ) return(character(0)) 7 | snippet <- ' 8 | import reflect.runtime.{universe => ru} 9 | ru.typeOf[@{type}].members.map(_.toString).toSet.filter(_.startsWith("method ")).map(_.substring(7)).filter(!_.startsWith("$")).toArray 10 | ' 11 | env <- attr(x,"rscalaReferenceEnvironment") 12 | snippet <- sub("@\\{type\\}",env[['type']],snippet) 13 | methods <- scalaInvoke(env[['details']], snippet, list(), parent.frame(1)) 14 | grep(pattern, methods, value=TRUE) 15 | } 16 | -------------------------------------------------------------------------------- /R/rscala/R/is.scalaReference.R: -------------------------------------------------------------------------------- 1 | #' Test for Scala Reference 2 | #' 3 | #' @param x An arbitrary R object. 4 | #' 5 | #' @return Logical indicating whether \code{x} is an rscala reference. 6 | #' @export 7 | #' 8 | #' @examples 9 | #' is.scalaReference(c(1,2)) 10 | #' 11 | is.scalaReference <- function(x) inherits(x,"rscalaReference") 12 | -------------------------------------------------------------------------------- /R/rscala/R/ops.R: -------------------------------------------------------------------------------- 1 | #' Evaluation Operator 2 | #' 3 | #' This operator compiles and executes a snippet of Scala code. All definitions 4 | #' are \emph{local} to the supplied Scala snippet. Subsequent uses of the same 5 | #' code snippet skips the time-consuming compilation step. The return value is 6 | #' a vector or matrix of \R's basic types (if possible) or an rscala reference 7 | #' (otherwise). 8 | #' 9 | #' @param bridge A Scala bridge. 10 | #' @param snippet String providing a Scala code snippet. 11 | #' 12 | #' @return Returns a vector or matrix of \R's basic types (if possible) or an 13 | #' rscala reference (otherwise). 14 | #' @seealso \code{\link{^.rscalaBridge}}, \code{\link{+.rscalaBridge}}, 15 | #' \code{\link{scala}} 16 | #' @export 17 | #' @examples \donttest{ 18 | #' s <- scala() 19 | #' s * 'scala.util.Random.nextDouble() <= 0.75' 20 | #' s(mean=10, sd=2.5) * 'mean + sd * scala.util.Random.nextGaussian()' 21 | #' close(s) 22 | #' } 23 | #' 24 | '*.rscalaBridge' <- function(bridge, snippet) { 25 | details <- attr(bridge,"details") 26 | args <- if ( is.function(bridge) ) list() else bridge 27 | scalaInvoke(details, snippet, args, parent.frame(1), withNames=TRUE) 28 | } 29 | 30 | #' Evaluation Operator Returning a Reference and Transcompile Operator 31 | #' 32 | #' This operator is equivalent to \code{\link{*.rscalaBridge}}, except the 33 | #' return value is always an rscala reference. This operator also allows (a 34 | #' small subset of) R code to be transcompiled to Scala code and produces an 35 | #' rscala reference to an anonymous Scala function. 36 | #' 37 | #' @inheritParams *.rscalaBridge 38 | #' 39 | #' @return Returns an rscala reference. 40 | #' @seealso \code{\link{*.rscalaBridge}}, \code{\link{+.rscalaBridge}}, 41 | #' \code{\link{scala}} 42 | #' @export 43 | #' @examples \donttest{ 44 | #' s <- scala() 45 | #' x <- s ^ 'new scala.util.Random()' # These two lines ... 46 | #' x <- s $ .new_scala.util.Random() # ... are equivalent 47 | #' s(rng=x) * 'rng.nextDouble()' 48 | #' f <- s ^ function(x=scalaType('Double')) { pi - x } 49 | #' f$apply(3.14) 50 | #' s(n=10L, mapper=s ^ function(x=scalaType("Int")) { 2 * x }) * "Array.tabulate(n)(mapper)" 51 | #' logStdNormalDensity <- s ^ function(x=scalaType("Double"), mean=0.0, sd=1.0) { 52 | #' variance <- sd^2 53 | #' -0.5*log(2*pi*variance) - 0.5/variance * (x-mean)^2 54 | #' } 55 | #' identical(logStdNormalDensity$apply(1.0), dnorm(1.0, log=TRUE)) 56 | #' close(s) 57 | #' } 58 | #' 59 | '^.rscalaBridge' <- function(bridge, snippet) { 60 | details <- attr(bridge,"details") 61 | args <- if ( is.function(bridge) ) list() else bridge 62 | if ( ! is.function(snippet) ) scalaInvoke(details, paste0(".",snippet), args, parent.frame(1), withNames=TRUE) 63 | else { 64 | if ( any(sapply(args,function(x) inherits(x,"rscalaType"))) ) stop("'scalaType' arguments must be in the function itself, not the Scala bridge.") 65 | ast <- as.list(snippet) 66 | args2 <- lapply(ast[-length(ast)],eval,envir=environment(snippet)) 67 | ast <- ast[[length(ast)]] 68 | details <- attr(bridge,"details") 69 | if ( details[["disconnected"]] ) scalaConnect(details) 70 | symbolEnv <- new.env(parent=emptyenv()) 71 | transcompilation <- r2scala(ast,details[["debugTranscompilation"]],symbolEnv,details[["transcompileSubstitute"]]) 72 | returnString <- if ( exists("_returnType",envir=symbolEnv) ) paste0(": ",get("_returnType",envir=symbolEnv)) else "" 73 | header <- details[["transcompileHeader"]] 74 | header <- if ( length(header) > 0 ) paste0(paste0(header,collapse="\n"),"\n") else NULL 75 | whichInternal <- if ( length(args2) == 0 ) logical(0) else sapply(args2,function(x) inherits(x,"rscalaType")) 76 | internalArgs <- args2[whichInternal] 77 | args <- c(args,args2[!whichInternal]) 78 | internalArgsList <- if ( length(internalArgs) > 0 ) paste0(names(internalArgs),": ",internalArgs,collapse=", ") else NULL 79 | scalaInvoke(details, paste0(".",header,"def self(", internalArgsList, ")",returnString," = ", transcompilation, "\nself _"), args, parent.frame(1), withNames=TRUE, 80 | transcompileInfo=list(argTypes=internalArgs,original=snippet)) 81 | } 82 | } 83 | 84 | #' Declaration Operator 85 | #' 86 | #' This operator compiles and executes a snippet of Scala code \emph{in Scala's 87 | #' global environment}, where subsequent uses of the same code snippet do 88 | #' \emph{not} skip the time-consuming compilation step and the return value is 89 | #' \code{NULL}. As such, this operator is used to define \emph{global} imports, 90 | #' objects, classes, methods, etc. 91 | #' 92 | #' @inheritParams *.rscalaBridge 93 | #' 94 | #' @return Returns \code{NULL}, invisibly. 95 | #' @seealso \code{\link{*.rscalaBridge}}, \code{\link{^.rscalaBridge}}, 96 | #' \code{\link{scala}} 97 | #' @export 98 | #' @examples \donttest{ 99 | #' s <- scala() 100 | #' s + ' 101 | #' import scala.util.Random.nextInt 102 | #' import scala.math.{Pi, log, exp, sqrt} 103 | #' val const = -log(sqrt(2*Pi)) 104 | #' def dnorm(x: Double, mean: Double, sd: Double, logScale: Boolean) = { 105 | #' val z = ( x - mean ) / sd 106 | #' val result = const - log(sd) - z * z / 2 107 | #' if ( logScale ) result else exp(result) 108 | #' } 109 | #' ' 110 | #' s $ const() 111 | #' s $ nextInt(100L) 112 | #' s $ dnorm(8, 10, 2, FALSE) 113 | #' close(s) 114 | #' } 115 | #' 116 | '+.rscalaBridge' <- function(bridge, snippet) { 117 | if ( ( ! is.function(bridge) ) && ( length(bridge) > 0 ) ) stop("When using the `+` operator, no arguments may be supplied to the bridge.") 118 | scalaInvoke(attr(bridge,"details"), snippet, NULL, parent.frame(1)) 119 | } 120 | 121 | -------------------------------------------------------------------------------- /R/rscala/R/print.R: -------------------------------------------------------------------------------- 1 | #' @export 2 | #' 3 | print.rscalaBridge <- function(x, ...) { 4 | cat(toString(x, ...),"\n",sep="") 5 | } 6 | 7 | #' @export 8 | # 9 | toString.rscalaBridge <- function(x, ...) { 10 | if ( is.function(x) ) "Scala bridge" 11 | else "Scala bridge with a parameter list" 12 | } 13 | 14 | #' @export 15 | #' 16 | print.rscalaReference <- function(x, ...) { 17 | env <- attr(x,"rscalaReferenceEnvironment") 18 | if ( exists("original",envir=env) ) { 19 | func <- get("original",envir=env) 20 | if ( ! is.null(func) ) print(func) 21 | } 22 | cat(toString(x, ...),"\n",sep="") 23 | } 24 | 25 | #' @export 26 | # 27 | toString.rscalaReference <- function(x, ...) { 28 | env <- attr(x,"rscalaReferenceEnvironment") 29 | paste0("rscala reference of type ",env[["type"]]) 30 | } 31 | 32 | #' @export 33 | #' 34 | print.rscalaSub <- function(x, ...) { 35 | cat(toString(x, ...),"\n",sep="") 36 | } 37 | 38 | #' @export 39 | # 40 | toString.rscalaSub <- function(x, ...) { 41 | "rscala stub" 42 | } 43 | 44 | #' @export 45 | #' 46 | toString.rscalaType <- function(x, ...) { 47 | paste0(unclass(x)) 48 | } 49 | 50 | #' @export 51 | #' 52 | print.rscalaType <- function(x, ...) { 53 | cat(toString(x, ...),"\n",sep="") 54 | } 55 | -------------------------------------------------------------------------------- /R/rscala/R/scalaDevelDeployJARs.R: -------------------------------------------------------------------------------- 1 | #' Deploy JAR Files into the Package File System 2 | #' 3 | #' This function copies the JAR files to the appropriate directories of the R 4 | #' package source. Specifically, source JAR files go into \code{(PKGHOME)/java} 5 | #' and binary JAR files go into \code{(PKGHOME)/inst/java/scala-(VERSION)}, 6 | #' where \code{(PKGHOME)} is the package home and \code{(VERSION)} is the major 7 | #' Scala version (e.g., 2.13). 8 | #' 9 | #' @param name The package name (as a string). 10 | #' @param root The file system path to package root directory (as a string). 11 | #' @param srcJAR The file system path to source JAR file (as a string). 12 | #' @param binJARs A named character vector of file system paths, where each name 13 | #' is a Scala major version (e.g., \code{"2.13"}.) 14 | #' 15 | #' @export 16 | #' 17 | scalaDevelDeployJARs <- function(name, root, srcJAR, binJARs) { 18 | if ( missing(name) || ( ! is.vector(name) ) || ( ! is.character(name) ) || ( length(name) != 1 ) || ( name == "" ) ) stop("'name' is mispecified.") 19 | if ( missing(root) || ( ! is.vector(root) ) || ( ! is.character(root) ) || ( length(root) != 1 ) || ( ! dir.exists(root) ) ) stop("'root' directory does not exist.") 20 | if ( ! file.exists(file.path(root,"DESCRIPTION")) ) stop("'root' does not appear to be a package root directory.") 21 | if ( missing(srcJAR) || ( ! is.vector(srcJAR) ) || ( ! is.character(srcJAR) ) || ( length(srcJAR) != 1 ) ) stop("'srcJAR' must be a path to JAR file.") 22 | if ( ! file.exists(srcJAR) ) stop("'srcJAR' does not exists in the file system.") 23 | if ( missing(binJARs) || ( ! is.vector(binJARs) ) || ( ! is.character(binJARs) || ( length(binJARs) == 0 ) || is.null(names(binJARs))) ) stop("'binJARs' must be a named vector of paths to JAR files.") 24 | if ( ! all(file.exists(binJARs)) ) stop("'binJARs' has elements that do not exists in the file system.") 25 | binDir <- file.path(root,"inst","java") 26 | for ( index in seq_along(binJARs) ) { 27 | v <- scalaMajorVersion(names(binJARs)[index]) 28 | destDir <- file.path(binDir,sprintf("scala-%s",v)) 29 | dir.create(destDir,FALSE,TRUE) 30 | file.copy(binJARs[index],file.path(destDir,paste0(name,".jar")),TRUE) 31 | } 32 | srcDir <- file.path(root,"java") 33 | dir.create(srcDir,FALSE,TRUE) 34 | file.copy(srcJAR,file.path(srcDir,paste0(name,"-source.jar")),TRUE) 35 | invisible() 36 | } 37 | 38 | -------------------------------------------------------------------------------- /R/rscala/R/scalaDisconnect.R: -------------------------------------------------------------------------------- 1 | #' Temporarily Disconnect Scala by Closing Connections 2 | #' 3 | #' This function temporarily disconnects a Scala bridge by closing its 4 | #' associated socket connections. The primary place where this function is used 5 | #' is at the end of examples of packages that depend on rscala (because, under 6 | #' some versions of R, "\code{R CMD check --as-cran}" does not permit 7 | #' connections to persist after an example ends). 8 | #' 9 | #' @param bridge A Scala bridge. 10 | #' @export 11 | #' @examples \donttest{ 12 | #' showConnections() 13 | #' s <- scala() 14 | #' showConnections() # No additional connections yet. 15 | #' s * "3+4" 16 | #' showConnections() # Now there are two additional connections. 17 | #' scalaDisconnect() 18 | #' showConnections() # The new connections are gone. 19 | #' s * "3+4" 20 | #' showConnections() # New connections are established as needed. 21 | #' close(s) 22 | #' } 23 | #' 24 | scalaDisconnect <- function(bridge=scalaFindBridge()) { 25 | details <- attr(bridge,"details") 26 | if ( details[["disconnected"]] ) return(invisible()) 27 | scalaLastEngine(details) 28 | if ( details[["interrupted"]] ) return(invisible()) 29 | socketOut <- details[["socketOut"]] 30 | socketIn <- details[["socketIn"]] 31 | wb(socketOut,PCODE_SUSPEND) 32 | close(socketIn) 33 | close(socketOut) 34 | assign("disconnected",TRUE,envir=details) 35 | invisible() 36 | } 37 | -------------------------------------------------------------------------------- /R/rscala/R/scalaFindBridge.R: -------------------------------------------------------------------------------- 1 | #' Find a Scala Bridge 2 | #' 3 | #' This function attempts to find an instance of a Scala bridge based on an 4 | #' rscala reference or by searching the environment path. 5 | #' 6 | #' @param reference Either: i. An rscala reference, or ii. \code{NULL} (in which 7 | #' case the environment path is searched). 8 | #' 9 | #' @return A Scala bridge. 10 | #' @export 11 | #' 12 | scalaFindBridge <- function(reference=NULL) { 13 | if ( ! is.null(reference) ) { 14 | mkBridge(attr(reference,"rscalaReferenceEnvironment")[["details"]]) 15 | } else { 16 | counter <- 2 17 | while ( TRUE ) { 18 | frame <- parent.frame(counter) 19 | w <- which(sapply(ls(envir=frame),function(x) class(get(x,envir=frame)))=="rscalaBridge") 20 | if ( length(w) == 1 ) return(get(names(w),envir=frame)) 21 | if ( length(w) > 1 ) stop("Multiple Scala instances were found in the same environment.") 22 | if ( identical(frame,.GlobalEnv) ) stop("Cannot find a Scala bridge.") 23 | counter <- counter + 1 24 | } 25 | } 26 | } 27 | -------------------------------------------------------------------------------- /R/rscala/R/scalaLast.R: -------------------------------------------------------------------------------- 1 | #' Retrieve the Last Scala Computation 2 | #' 3 | #' This function retrieves the last result from the supplied Scala bridge. 4 | #' 5 | #' @param bridge A Scala bridge 6 | #' 7 | #' @export 8 | #' @seealso \code{\link{scalaFindBridge}} 9 | #' 10 | #' @examples \donttest{ 11 | #' s <- scala() 12 | #' s * "2+3" 13 | #' scalaLast(s) 14 | #' close(s) 15 | #' } 16 | #' 17 | scalaLast <- function(bridge=scalaFindBridge()) { 18 | details <- attr(bridge,"details") 19 | last <- scalaLastEngine(details) 20 | if ( details[["interrupted"]] ) invisible() else last 21 | } 22 | 23 | scalaLastEngine <- function(details) { 24 | checkConnection(details) 25 | if ( details[["interrupted"]] ) { 26 | cat("<< waiting for previously interrupted computation to finish >>\n") 27 | assign("interrupted",FALSE,envir=details) 28 | pop(details) 29 | } 30 | details[["last"]] 31 | } 32 | -------------------------------------------------------------------------------- /R/rscala/R/scalaLazy.R: -------------------------------------------------------------------------------- 1 | #' Lazily Execute Functions on a Scala Bridge 2 | #' 3 | #' @param functions A single function or list of functions. Each function takes 4 | #' a Scala bridge as its only argument. These functions are called immediately 5 | #' after the next time the bridge is connected. These functions are where 6 | #' setup code should go, like \emph{global} imports, objects, classes, 7 | #' methods, etc. For example, it might equal \code{function(s) { s + 'import 8 | #' scala.util.Random' }}. \strong{Note} the use of the declaration operator 9 | #' \code{+} instead of the operators \code{*} or \code{^}. 10 | #' @param bridge A Scala bridge from the \code{scala} function. 11 | #' 12 | #' @return Returns \code{NULL}, invisibly. 13 | #' 14 | #' @export 15 | #' @seealso \code{\link{scalaFindBridge}} 16 | #' 17 | #' @examples \donttest{ 18 | #' s <- scala() 19 | #' scalaLazy(function(s) { s + 'import scala.util.Random' }) 20 | #' s$.new_Random()$nextDouble() 21 | #' close(s) 22 | #' } 23 | #' 24 | scalaLazy <- function(functions, bridge=scalaFindBridge()) { 25 | details <- if ( inherits(bridge,"rscalaBridge") ) attr(bridge,"details") else bridge 26 | if ( details[["disconnected"]] ) { 27 | assign("pendingCallbacks",c(get("pendingCallbacks",envir=details),functions),envir=details) 28 | } else { 29 | bridge2 <- if ( inherits(bridge,"rscalaBridge") ) bridge else mkBridge(bridge) 30 | if ( is.list(functions) ) lapply(functions, function(f) f(bridge2)) 31 | else functions(bridge2) 32 | } 33 | invisible() 34 | } 35 | -------------------------------------------------------------------------------- /R/rscala/R/scalaMemory.R: -------------------------------------------------------------------------------- 1 | #' Get or Set Memory Available to Scala 2 | #' 3 | #' Depending on the argument type, this function has several uses related to 4 | #' memory in Scala. 5 | #' 6 | #' @param x If the argument is a string (e.g., "8G" or "512M"), the function 7 | #' sets the default maximum heap size for new instances of Scala bridges 8 | #' created by the function \code{\link{scala}}. If the argument is missing, 9 | #' the current default maximum heap size for new instances is returned. Set 10 | #' the argument to \code{NULL} to disable this global option, and therefore 11 | #' use \pkg{rscala}'s default. If the argument is a Scala bridge, the 12 | #' function returns a numeric vector giving the current heap size and the 13 | #' maximum heap size, in megabytes. 14 | #' 15 | #' @export 16 | #' @seealso \code{\link{scala}} 17 | #' 18 | #' @examples \dontrun{ 19 | #' scalaMemory("1G") 20 | #' } 21 | #' 22 | scalaMemory <- function(x) { 23 | if ( missing(x) ) getOption("rscala.heap.maximum") 24 | else if ( inherits(x,"rscalaBridge") ) { 25 | x * 'Array((Runtime.getRuntime.totalMemory / ( 1024 * 1024 )).toInt, (Runtime.getRuntime.maxMemory / ( 1024 * 1024 )).toInt)' 26 | } else { 27 | if ( ! is.null(x) ) x <- as.character(x)[1] 28 | options(rscala.heap.maximum=x) 29 | invisible() 30 | } 31 | } 32 | -------------------------------------------------------------------------------- /R/rscala/R/scalaPull.R: -------------------------------------------------------------------------------- 1 | #' @rdname scalaPush 2 | #' 3 | #' @param reference An rscala reference. 4 | #' 5 | #' @export 6 | #' 7 | scalaPull <- function(reference, method, ...) { 8 | if ( ! is.scalaReference(reference) ) stop("An rscala reference is required.") 9 | bridge <- scalaFindBridge(reference) 10 | pullers <- get("pullers",envir=attr(bridge,"details")) 11 | pullers[[method]](reference, bridge, ...) 12 | } 13 | 14 | scalaPull.generic <- function(reference, bridge) { 15 | type <- scalaType(reference) 16 | if ( type == "org.ddahl.rscala.RObject" ) unserialize(reference$x()) 17 | else if ( type == "List[org.ddahl.rscala.RObject]" ) { 18 | pair <- bridge(arr=reference) ^ '(arr.flatMap(_.x).toArray, arr.scanLeft(1)((sum,y) => sum + y.x.length).toArray)' 19 | bytes <- pair$"_1"() 20 | sizes <- pair$"_2"() 21 | lapply(seq_along(sizes[-1]), function(i) { 22 | unserialize(bytes[sizes[i]:(sizes[i+1]-1)]) 23 | }) 24 | } else stop("Reference is not an RObject or a List[RObject].") 25 | } 26 | 27 | scalaPull.list <- function(reference, bridge) { 28 | if ( ! grepl("List\\d+",scalaType(reference)) ) stop("This is not a reference to a list.") 29 | names <- reference$names() 30 | asIs <- reference$asIs() 31 | x <- lapply(seq_along(names),function(i) { 32 | x <- eval(parse(text=paste0("reference$",names[i],"()"))) 33 | if ( asIs[i] ) I(x) else x 34 | }) 35 | names(x) <- names 36 | if ( ! reference$isDataFrame() ) x 37 | else { 38 | rowNamesOptions <- reference$rowNames() 39 | rowNames <- if ( rowNamesOptions$isDefined() ) rowNamesOptions$get() else NULL 40 | as.data.frame(x,row.names=rowNames,stringsAsFactors=FALSE) 41 | } 42 | } 43 | 44 | scalaPull.arrayOfMatrices <- function(reference, bridge, mode="double") { 45 | modeInfo <- if ( mode == "double" ) list(double(0),"Double") 46 | else if ( mode == "integer" ) list(integer(0),"Int") 47 | else if ( mode == "logical" ) list(logical(0),"Boolean") 48 | else if ( mode == "character" ) list(character(0),"String") 49 | else stop("Unsupport 'mode'.") 50 | modeZero <- modeInfo[[1]] 51 | modeType <- modeInfo[[2]] 52 | if ( gsub("<>",modeType,"Array[Array[Array[<>]]]") != scalaType(reference) ) stop("This is not a reference to an array of matrices (i.e., Array[Array[Array[_]]]).") 53 | dims <- bridge(reference) * ' 54 | reference.map(X => if ( X == null ) Array(0,0) else Array(X.length,X(0).length)) 55 | ' 56 | data <- bridge(reference) * gsub("<>",modeType,' 57 | reference.flatMap(X => if ( X == null ) Array.ofDim[<>](0,0) else X).flatten 58 | ') 59 | offset <- 1 60 | result <- vector(nrow(dims),mode="list") 61 | for ( i in 1:nrow(dims) ) { 62 | d <- dims[i,] 63 | pd <- prod(d) 64 | dt <- if ( pd == 0 ) modeZero else data[offset:(offset+pd-1)] 65 | result[[i]] <- matrix(dt,nrow=d[1],byrow=TRUE) 66 | offset <- offset + pd 67 | } 68 | result 69 | } 70 | -------------------------------------------------------------------------------- /R/rscala/R/scalaPush.R: -------------------------------------------------------------------------------- 1 | #' Push and Pull Objects Between R and Scala 2 | #' 3 | #' The push function serializes an R object to Scala and the push function does 4 | #' the opposite. A couple of built push and pull methods are provided, namely 5 | #' \code{"generic"} and \code{"list"}. The \code{"generic"} method serializes an 6 | #' arbitrary R object to an instance of \code{RObject} in Scala. Since the 7 | #' \code{RObject} merely contains an array of bytes, the \code{RObject} is 8 | #' really only useful as storage for later unserialization. The \code{"generic"} 9 | #' method has an optional \code{as.is} argument which is either \code{TRUE} to 10 | #' cause the list to serialized as a single object or \code{FALSE} to cause each 11 | #' element of the list to the serialized individually. More methods may be added 12 | #' using the functions \code{\link{scalaPushRegister}} and 13 | #' \code{\link{scalaPullRegister}}. 14 | #' 15 | #' @param x An R object. 16 | #' @param method A string giving the specific 'push' or 'pull' method to use. 17 | #' @param bridge A Scala bridge. 18 | #' @param ... Other arguments passed to specialized push and pull functions. 19 | #' 20 | #' @seealso \code{\link{scalaPushRegister}}, \code{\link{scalaPullRegister}} 21 | #' @export 22 | #' @examples \donttest{ 23 | #' s <- scala() 24 | #' 25 | #' s(rn=scalaPush(rnorm),n=5) * 'R.evalD1("%-(%-)",rn,n)' 26 | #' 27 | #' mtcarsRef <- scalaPush(mtcars, "list") 28 | #' mtcarsRef$names() 29 | #' mtcarsRef$mpg() 30 | #' mtcars2 <- scalaPull(mtcarsRef, "list") 31 | #' identical(mtcars, mtcars2) 32 | #' 33 | #' # Oops, the variable names are bad... 34 | #' tryCatch(ref <- scalaPush(iris, "list"), error=function(e) e) 35 | #' 36 | #' # ... so let's clean up the variable names. 37 | #' irisCleaned <- iris 38 | #' names(irisCleaned) <- gsub("\\W","_",names(iris)) 39 | #' irisCleaned$Species <- as.character(iris$Species) 40 | #' ref2 <- scalaPush(irisCleaned, "list") 41 | #' scalaType(ref2) 42 | #' ref2$Sepal_Length() 43 | #' irisCleaned2 <- scalaPull(ref2,"list") 44 | #' identical(irisCleaned, irisCleaned2) 45 | #' 46 | #' close(s) 47 | #' } 48 | #' 49 | scalaPush <- function(x, method="generic", bridge=scalaFindBridge(), ...) { 50 | pushers <- get("pushers",envir=attr(bridge,"details")) 51 | pushers[[method]](x, bridge, ...) 52 | } 53 | 54 | scalaPush.generic <- function(x, bridge, as.is=FALSE) { 55 | if ( is.list(x) && ( ! as.is ) ) { 56 | bridge(len=length(x)) ^ ' 57 | List.tabulate(len) { i => 58 | R.evalObject("x[[%-]]",i+1) 59 | } 60 | ' 61 | } else { 62 | bridge$.R.evalObject('x') 63 | } 64 | } 65 | 66 | scalaPush.list <- function(x, bridge) { 67 | if ( ! is.list(x) ) stop("Object is not a list.") 68 | uniqueNames <- unique(names(x)) 69 | if ( ( length(uniqueNames) != length(x) ) || ( any(uniqueNames=="") ) ) stop("All items must be named.") 70 | if ( any(grepl("\\W",uniqueNames)) ) { 71 | stop(paste0("The following variable names are problematic: ",paste0(uniqueNames[grepl("\\W",uniqueNames)],collapse=", "))) 72 | } 73 | asIs <- lapply(x,function(y) if ( inherits(y,"AsIs") ) "true" else "false") 74 | types <- lapply(x,function(y) { 75 | type <- typeof(y) 76 | if ( type == "double" ) "Double" 77 | else if ( type == "integer" ) "Int" 78 | else if ( type == "logical" ) "Boolean" 79 | else if ( type == "character" ) "String" 80 | else stop(paste0("Unsupported type: ",type)) 81 | }) 82 | shapes <- lapply(x,function(y) { 83 | if ( is.matrix(y) ) c("Array[Array[","]]") 84 | else { 85 | forceVector <- inherits(y,"AsIs") 86 | if ( ( ! forceVector ) && ( length(y) == 1L ) ) c("","") 87 | else c("Array[","]") 88 | } 89 | }) 90 | fullTypes <- lapply(seq_along(types),function(i) paste0(shapes[[i]][1],types[[i]],shapes[[i]][2])) 91 | names <- names(types) 92 | rowNameStr <- if ( is.data.frame(x) && ! all(row.names(x) == as.character(seq_len(nrow(x)))) ) { 93 | paste0("Some(Array(",paste0('"',row.names(x),'"',collapse=","),"))") 94 | } else "None" 95 | definition <- paste0("(\n",paste0(" val ",names,": ",fullTypes,collapse=",\n"),"\n) {\n", 96 | " val names = Array(",paste0('"',names,'"',collapse=","),")\n", 97 | " val asIs = Array(",paste0(asIs,collapse=","),")\n", 98 | " val isDataFrame = ",if (is.data.frame(x)) "true" else "false","\n", 99 | " val rowNames: Option[Array[String]] = ",rowNameStr,"\n", 100 | "}") 101 | name <- paste0("List",bridge(x=definition) * 'math.abs(x.hashCode).toString') 102 | definition <- paste0("class ",name,definition) 103 | bridge + definition 104 | f <- eval(parse(text=paste0("bridge$.new_",name))) 105 | args <- lapply(seq_len(length(x)), function(j) x[[j]]) 106 | reference <- do.call(f,args) 107 | reference 108 | } 109 | 110 | scalaPush.arrayOfMatrices <- function(x, bridge, mode="double") { 111 | if ( ! is.list(x) ) stop("Object is not a list.") 112 | if ( ! all(sapply(x,is.matrix)) ) stop("Not every element of the list is a matrix.") 113 | modeInfo <- if ( mode == "double" ) list(as.double, "Double") 114 | else if ( mode == "integer" ) list(as.integer,"Int") 115 | else if ( mode == "logical" ) list(as.logical,"Boolean") 116 | else if ( mode == "character" ) list(as.character,"String") 117 | else stop("Unsupport 'mode'.") 118 | modeFunc <- modeInfo[[1]] 119 | modeType <- modeInfo[[2]] 120 | ref <- bridge(dims=sapply(x,dim), data=unlist(lapply(x, function(y) modeFunc(y)))) ^ gsub("<>",modeType,' 121 | val len = dims(0).length 122 | var result = new Array[Array[Array[<>]]](len) 123 | var offset = 0 124 | var b = 0 125 | while ( b < len ) { 126 | val nrows = dims(0)(b) 127 | val ncols = dims(1)(b) 128 | result(b) = Array.tabulate(nrows,ncols) { (i,j) => 129 | data(offset+nrows*j+i) 130 | } 131 | b += 1 132 | offset += ncols*nrows 133 | } 134 | result 135 | ') 136 | } 137 | -------------------------------------------------------------------------------- /R/rscala/R/scalaPushRegister.R: -------------------------------------------------------------------------------- 1 | #' Register Functions to Push and Pull Between R and Scala 2 | #' 3 | #' The 'rscala' package provides support for serializing objects between R and Scala. 4 | #' These registration functions allows 5 | #' additional, more-specialized push and pull methods to be added. 6 | #' Package developers may want to call these registration functions in the package's 7 | #' \code{\link{.onLoad}} function. 8 | #' 9 | #' @param pusher A function whose first two arguments are as shown in the example below. 10 | #' Other arguments can be used as additional arguments. 11 | #' @param puller A function whose first two arguments are as shown in the example below. 12 | #' Other arguments can be used as additional arguments. 13 | #' @param method A string giving the name of the specific 'push' or 'pull' method. 14 | #' @param bridge A Scala bridge. 15 | #' @seealso \code{\link{scalaPush}}, \code{\link{scalaPull}} 16 | #' @export 17 | #' 18 | #' @examples \donttest{ 19 | #' s <- scala() 20 | #' 21 | #' name <- "Grace" 22 | #' nameAsRObject <- scalaPush(name,"generic") # Basic serialization 23 | #' scalaType(nameAsRObject) 24 | #' identical(name,scalaPull(nameAsRObject,"generic")) 25 | #' 26 | #' scalaPush.character <- function(x, bridge) { 27 | #' if ( is.character(x) && ( length(x) == 1L ) ) bridge(x=x) ^ 'x' 28 | #' else stop("'x' should be a character vector.") 29 | #' } 30 | #' scalaPushRegister(scalaPush.character, "character") 31 | #' nameAsString <- scalaPush(name, "character", s) # More specific serialization 32 | #' scalaType(nameAsString) 33 | #' 34 | #' scalaPull.character <- function(reference, bridge) { 35 | #' if ( scalaType(reference) == "String" ) reference$toString() 36 | #' else stop("'reference' should be a 'String'.") 37 | #' } 38 | #' scalaPullRegister(scalaPull.character, "character") 39 | #' identical(name,scalaPull(nameAsString,"character")) 40 | #' 41 | #' close(s) 42 | #' } 43 | #' 44 | scalaPushRegister <- function(pusher, method, bridge=scalaFindBridge()) { 45 | assign(method,pusher,envir=get("pushers",envir=attr(bridge,"details"))) 46 | } 47 | 48 | #' @rdname scalaPushRegister 49 | #' @export 50 | scalaPullRegister <- function(puller, method, bridge=scalaFindBridge()) { 51 | assign(method,puller,envir=get("pullers",envir=attr(bridge,"details"))) 52 | } 53 | -------------------------------------------------------------------------------- /R/rscala/R/scalaType.R: -------------------------------------------------------------------------------- 1 | #' Get or Specify a Scala Type 2 | #' 3 | #' This function gets the Scala type of an rscala reference. It also, together 4 | #' with the associated convenience objects, specifies a Scala type for 5 | #' transcompilation purposes. 6 | #' 7 | #' The convenience objects are of the form \code{stXY} (where \code{X} is in 8 | #' \code{{I, D, L, R, S}} and \code{Y} is in \code{{0, 1, 2}}) as as indicated 9 | #' below: 10 | #' 11 | #' \itemize{ 12 | #' \item \code{I} corresponds to Scala's \code{Int} and R's \code{integer}. 13 | #' \item \code{D} corresponds to Scala's \code{Double} and R's \code{double}. 14 | #' \item \code{L} corresponds to Scala's \code{Boolean} and R's \code{logical}. 15 | #' \item \code{R} corresponds to Scala's \code{Byte} and R's \code{raw}. 16 | #' \item \code{S} corresponds to Scala's \code{String} and R's \code{character}. 17 | #' } 18 | #' 19 | #' \itemize{ 20 | #' \item \code{0} corresponds to a Scala primitive and an R length one vector. 21 | #' \item \code{1} corresponds to a Scala array and an R vector. 22 | #' \item \code{2} corresponds to a Scala array of arrays and an R matrix. 23 | #' } 24 | #' 25 | #' For example, \code{stS2} is equivalent to Scala's 26 | #' \code{scalaType("Array[Array[String]]")} and R's type for 27 | #' \code{matrix(character())}. Also, \code{stL1} is equivalent to Scala's 28 | #' \code{scalaType("Boolean")} and R's type for \code{logical(1)}. 29 | #' 30 | #' @param type An rscala reference or a character vector of length one giving a 31 | #' Scala type. 32 | #' 33 | #' @return An object of class \code{rscalaType} whose value is a character 34 | #' vector of length one indicating a Scala type. 35 | #' @format See 'Value' below. 36 | #' 37 | #' @export 38 | #' 39 | #' @examples 40 | #' scalaType("Double") 41 | #' stD0 42 | #' scalaType("Array[Byte]") 43 | #' stR1 44 | #' scalaType("Array[Array[Int]]") 45 | #' stI2 46 | #' 47 | scalaType <- function(type) { 48 | type <- if ( is.scalaReference(type) ) attr(type,"rscalaReferenceEnvironment")[["type"]] 49 | else if ( ( typeof(type) == "character" ) && ( length(type) == 1 ) ) type 50 | else stop("Illegal argument.") 51 | structure(type, class="rscalaType") 52 | } 53 | 54 | #' @rdname scalaType 55 | #' @export 56 | stI0 <- scalaType("Int") 57 | 58 | #' @rdname scalaType 59 | #' @export 60 | stD0 <- scalaType("Double") 61 | 62 | #' @rdname scalaType 63 | #' @export 64 | stL0 <- scalaType("Boolean") 65 | 66 | #' @rdname scalaType 67 | #' @export 68 | stR0 <- scalaType("Byte") 69 | 70 | #' @rdname scalaType 71 | #' @export 72 | stS0 <- scalaType("String") 73 | 74 | #' @rdname scalaType 75 | #' @export 76 | stI1 <- scalaType("Array[Int]") 77 | 78 | #' @rdname scalaType 79 | #' @export 80 | stD1 <- scalaType("Array[Double]") 81 | 82 | #' @rdname scalaType 83 | #' @export 84 | stL1 <- scalaType("Array[Boolean]") 85 | 86 | #' @rdname scalaType 87 | #' @export 88 | stR1 <- scalaType("Array[Byte]") 89 | 90 | #' @rdname scalaType 91 | #' @export 92 | stS1 <- scalaType("Array[String]") 93 | 94 | #' @rdname scalaType 95 | #' @export 96 | stI2 <- scalaType("Array[Array[Int]]") 97 | 98 | #' @rdname scalaType 99 | #' @export 100 | stD2 <- scalaType("Array[Array[Double]]") 101 | 102 | #' @rdname scalaType 103 | #' @export 104 | stL2 <- scalaType("Array[Array[Boolean]]") 105 | 106 | #' @rdname scalaType 107 | #' @export 108 | stR2 <- scalaType("Array[Array[Byte]]") 109 | 110 | #' @rdname scalaType 111 | #' @export 112 | stS2 <- scalaType("Array[Array[String]]") 113 | -------------------------------------------------------------------------------- /R/rscala/R/scalaVersionJARs.R: -------------------------------------------------------------------------------- 1 | #' JAR Files for Support Scala Versions 2 | #' 3 | #' This function returns a named list whose elements give the file system paths of the JAR files for the supported major versions of Scala. 4 | #' 5 | #' @return A list whose names correspond to Scala major versions and whose elements are file system paths. 6 | #' @export 7 | #' 8 | #' @examples 9 | #' scalaVersionJARs() 10 | #' 11 | scalaVersionJARs <- function() { 12 | pkgHome <- if ( identical(Sys.getenv("R_INSTALL_PKG"),"rscala") ) file.path(Sys.getenv("R_PACKAGE_DIR"),"inst") else find.package("rscala") 13 | majorVersions <- gsub("^scala-(.*)","\\1",list.dirs(file.path(pkgHome,"java"),full.names=FALSE,recursive=FALSE)) 14 | if ( length(majorVersions) == 0 ) return(character(0)) 15 | result <- sapply(majorVersions, function(v) list.files(file.path(pkgHome,"java",paste0("scala-",v)),full.names=TRUE)) 16 | as.list(result[sapply(result, function(x) !is.null(x) && length(x) > 0)]) 17 | } 18 | -------------------------------------------------------------------------------- /R/rscala/R/sysdata.rda: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/R/rscala/R/sysdata.rda -------------------------------------------------------------------------------- /R/rscala/R/zzz.R: -------------------------------------------------------------------------------- 1 | ## Disable the potential installation of Scala during installation. 2 | ## 3 | #if ( identical(Sys.getenv("R_INSTALL_PKG"),"rscala") ) { 4 | # load(file.path("R","sysdata.rda")) 5 | # scalaConfig() 6 | #} 7 | 8 | -------------------------------------------------------------------------------- /R/rscala/README.md: -------------------------------------------------------------------------------- 1 | # rscala: Bridge Between 'R' and 'Scala' with Callbacks 2 | 3 | #### By David B. Dahl (Brigham Young University) 4 | 5 | The rscala package provides a bridge between R and Scala, enabling a user to 6 | exploit each language's respective strengths in a single project. The rscala 7 | package brings Scala and Java libraries into R with a simple interface. 8 | Specifically, Scala classes can be instantiated and methods of Scala classes 9 | can be called directly. Furthermore, arbitrary Scala code can be executed on 10 | the fly from within R and callbacks to R are supported. Conversely, rscala also 11 | enables arbitrary R code to be embedded within a Scala application. 12 | 13 | 14 | ## Installation 15 | 16 | In R, install the package by executing: 17 | 18 | ```R 19 | install.packages("remotes") 20 | remotes::install_github("dbdahl/rscala/R/rscala") 21 | ``` 22 | 23 | To install --- or check the compatability of your existing installation of --- 24 | Scala and Java, please execute: 25 | 26 | ```R 27 | rscala::scalaConfig() 28 | ``` 29 | 30 | Note that if only want to embed R in a Scala application, you don't need to 31 | install the package. Simply add the following line to the your SBT build.sbt 32 | file: 33 | 34 | ```scala 35 | libraryDependencies += "org.ddahl" %% "rscala" % "3.2.19" 36 | ``` 37 | Or if you're managing dependencies with Maven, you may add the following to 38 | your `pom.xml` file, replacing the version numbers for Scala and for this 39 | library as appropriate. 40 | ```xml 41 | 42 | org.ddahl 43 | rscala_2.13 44 | 3.2.19 45 | 46 | ``` 47 | 48 | ## Usage guides 49 | 50 | The original paper describing the software is: 51 | 52 | D. B. Dahl (2020), Integration of R and Scala using rscala, [**Journal of Statistical Software**](https://www.jstatsoft.org), 92:4, 1-18, *doi:10.18637/jss.v092.i04*. 53 | 54 | The citation information is available using: 55 | 56 | ```R 57 | citation("rscala") 58 | ``` 59 | 60 | An [updated version of the paper](https://github.com/dbdahl/rscala/blob/master/R/rscala/inst/doc/rscala.pdf?raw=true) 61 | is available [here](https://github.com/cran/rscala/blob/master/inst/doc/rscala.pdf?raw=true). 62 | 63 | ```R 64 | vignette("rscala") 65 | ``` 66 | 67 | The functionality of the software is also described and demonstrated in the 68 | help files: 69 | 70 | ```R 71 | library(help="rscala") 72 | library(rscala) 73 | example(scala) 74 | 75 | ``` 76 | 77 | 78 | ## Example packages built with rscala 79 | 80 | R extensions can be written using this package, as demonstrated by these 81 | packages: 82 | 83 | * [aibd](https://github.com/dbdahl/aibd) 84 | * [shallot](https://github.com/dbdahl/shallot) 85 | * [bamboo](https://github.com/dbdahl/bamboo) 86 | 87 | 88 | ## Resources 89 | 90 | * [Vignette](https://github.com/cran/rscala/blob/master/inst/doc/rscala.pdf?raw=true) describing the package usage. 91 | * [Git repository](https://github.com/dbdahl/rscala) containing source code and build & test scripts. 92 | * [Scaladoc](https://dahl.byu.edu/rscala/org/ddahl/rscala/RClient.html) for RClient class to access R from Scala. 93 | 94 | -------------------------------------------------------------------------------- /R/rscala/inst/CITATION: -------------------------------------------------------------------------------- 1 | bibentry(bibtype = "Article", 2 | title = "Integration of {R} and {Scala} Using {rscala}", 3 | author = person(given = c("David", "B."), 4 | family = "Dahl", 5 | email = "dahl@stat.byu.edu"), 6 | journal = "Journal of Statistical Software", 7 | year = "2020", 8 | volume = "92", 9 | number = "4", 10 | pages = "1--18", 11 | doi = "10.18637/jss.v092.i04", 12 | 13 | header = "To cite rscala in publications use:" 14 | ) 15 | 16 | -------------------------------------------------------------------------------- /R/rscala/inst/COPYRIGHT: -------------------------------------------------------------------------------- 1 | This package includes open source software components: 2 | 3 | ** rscala 4 | 5 | YEAR: 2013-2018 6 | COPYRIGHT HOLDER: David B. Dahl 7 | ORGANIZATION: Brigham Young University 8 | 9 | Project Website: https://github.com/dbdahl/rscala 10 | 11 | License Information: https://www.apache.org/licenses/LICENSE-2.0 12 | 13 | Related JAR: shallot*.jar 14 | 15 | -------------------------------------------------------------------------------- /R/rscala/inst/data-raw/sysdata: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env Rscript 2 | 3 | urls <- read.table(paste0("urls.txt"), header=TRUE, colClasses="character") 4 | save(urls, file="../../R/sysdata.rda", version=2) 5 | -------------------------------------------------------------------------------- /R/rscala/inst/data-raw/urls.txt: -------------------------------------------------------------------------------- 1 | software os arch version priority url md5sum 2 | java windows ^x86(-|_)64$ 17 50 https://byu.box.com/shared/static/6z39cqiwgavu2aa9abzw9elh1wwszxlg.zip ee4509eadec4d1398162120a2f6d4c54 3 | java mac ^x86(-|_)64$ 17 50 https://byu.box.com/shared/static/0un5w0z4ymyl4yzuk96rxn2g6s7wjz81.gz 7cfe7b66322cb4f9d42dd9839e4a8a45 4 | java linux ^x86(-|_)64$ 17 50 https://byu.box.com/shared/static/8jzcanepzchor5pgw9rzudky9hea3ktg.gz ce3ed32b9acd33b779f9255a402968e5 5 | java windows ^x86(-|_)64$ 11 50 https://byu.box.com/shared/static/qvs2mbdavtapdshblzxie7ux2c7vdzgx.zip 17b41763ad332124e816aa48f7a3f1fe 6 | java mac ^x86(-|_)64$ 11 50 https://byu.box.com/shared/static/95tn11gly297sh45zto3n0jb6uxvtphu.gz d44de64c4a1c2133b9b5c21600a0dfbb 7 | java linux ^x86(-|_)64$ 11 50 https://byu.box.com/shared/static/bzbmxwbi6f2ins09chfjh23szpvmmlo7.gz 0d7ccef71451af2579dfc51a7ec45773 8 | java windows ^x86(-|_)64$ 8 50 https://byu.box.com/shared/static/oe0yhw9blpu8hvw68so024jdynmtrc1k.zip 3b4fb7294c658629e3e841be6d54434b 9 | java mac ^x86(-|_)64$ 8 50 https://byu.box.com/shared/static/i5k2p517ihuqjfexsp58z0ulv9ak18jz.gz 77cd00fb7bfa9e3732a5b4ce24903566 10 | java linux ^x86(-|_)64$ 8 50 https://byu.box.com/shared/static/yuc35fmwaqgebw26k0ib02ry0s51blpw.gz 806755e9d331f8cb0b5c7b21f3f39001 11 | scala any any 2.11 50 https://byu.box.com/shared/static/wcos9t0i91m9xfhnkkfj9c5j9cwegv78.tgz 853bfdd9d89a99b2b54ad4e04111b88c 12 | scala any any 2.12 50 https://byu.box.com/shared/static/pc2zrk2cna8dojore95sja5h4ze97mpi.tgz e42ac31e64ad73e7dfd135c27c432a20 13 | scala any any 2.13 50 https://byu.box.com/shared/static/dzqtxa2qyexzi77o0udviili64dgbkkq.tgz 79e3cc22cbd363a6ea66c225113385c2 14 | sbt any any 1.8 50 https://byu.box.com/shared/static/ya3y5lh2afukpewc681mu6i1d0tly9qb.tgz 2486e6022886524e17eac9bd085ce779 15 | -------------------------------------------------------------------------------- /R/rscala/inst/doc/bootstrap-coverage.R: -------------------------------------------------------------------------------- 1 | makeConfidenceInterval <- function(p, n) { 2 | me <- qnorm(0.975) * sqrt( p * ( 1 - p ) / n ) 3 | c(estimate = p, lower = p - me, upper = p + me) 4 | } 5 | 6 | p1 <- 0.75 7 | p2 <- 0.35 8 | truth <- qnorm(p1) / qnorm(p2) 9 | n <- 100 10 | alpha <- 0.05 11 | 12 | 13 | 14 | cat("######## rscala implementation #1") 15 | 16 | library(rscala) 17 | s <- scala() 18 | 19 | coverage.rscala1 <- function(f, n, truth, p1, p2, nSamples, a, nIntervals) { 20 | coverage <- s(n = as.integer(n[1]), truth = as.double(truth[1]), 21 | p1 = as.double(p1[1]), p2 = as.double(p2[1]), 22 | nSamples = as.integer(nSamples[1]), a = as.double(a[1]), 23 | nIntervals = as.integer(nIntervals[1])) * ' 24 | import scala.util.Random 25 | import scala.concurrent.{Await, Future, duration} 26 | import scala.concurrent.ExecutionContext.Implicits.global 27 | 28 | def quantile(sorted: Array[Double], p: Double) = { 29 | val i = ((sorted.length - 1) * p).asInstanceOf[Int] 30 | val delta = (sorted.length-1) * p - i 31 | ( 1 - delta ) * sorted(i) + delta * sorted( i + 1 ) 32 | } 33 | 34 | def statistic(x: Array[Double]) = { 35 | scala.util.Sorting.quickSort(x) 36 | quantile(x, p1) / quantile(x, p2) 37 | } 38 | 39 | def resample(x: Array[Double], rng: Random) = Array.fill(x.length) { 40 | x(rng.nextInt(x.length)) 41 | } 42 | 43 | def ciContains(x: Array[Double], rng: Random) = { 44 | val bs = Array.fill(nSamples) { statistic(resample(x, rng)) } 45 | scala.util.Sorting.quickSort(bs) 46 | quantile(bs, a / 2) <= truth && truth <= quantile(bs, 1 - a / 2) 47 | } 48 | 49 | Await.result( Future.sequence( List.fill(nIntervals) { 50 | val dataset = R.evalD1("f(%-)", n) 51 | val seed = R.evalI0("sample(c(-1, 1), 1) * sample.int(2 ^ 31 - 1, 1)") 52 | val r = new Random(seed) 53 | Future { ciContains(dataset, r) } 54 | }), duration.Duration.Inf).count(identity) / nIntervals.toDouble 55 | ' 56 | makeConfidenceInterval(coverage, nIntervals) 57 | } 58 | 59 | 60 | 61 | cat("######## All the remaining implementation use the parallel package.") 62 | 63 | library(parallel) 64 | cluster <- makeCluster(detectCores()) 65 | 66 | 67 | 68 | cat("######## rscala implementation #2") 69 | 70 | clusterEvalQ(cluster, { 71 | library(rscala) 72 | s <- scala() 73 | ciContains.rscala2 <- function(f, n, truth, p1, p2, nSamples, a) { 74 | s(n = as.integer(n[1]), truth = as.double(truth[1]), 75 | p1 = as.double(p1[1]), p2 = as.double(p2[1]), 76 | nSamples = as.integer(nSamples[1]), a = as.double(a[1])) * ' 77 | import scala.util.Random 78 | 79 | def quantile(sorted: Array[Double], p: Double) = { 80 | val i = (( sorted.length - 1 ) * p).asInstanceOf[Int] 81 | val delta = ( sorted.length - 1 ) * p - i 82 | ( 1 - delta ) * sorted(i) + delta * sorted( i + 1 ) 83 | } 84 | 85 | def statistic(x: Array[Double]) = { 86 | scala.util.Sorting.quickSort(x) 87 | quantile(x, p1) / quantile(x, p2) 88 | } 89 | 90 | def resample(x: Array[Double], rng: Random) = Array.fill(x.length) { 91 | x(rng.nextInt(x.length)) 92 | } 93 | 94 | val x = R.evalD1("f(%-)", n) 95 | val seed = R.evalI0("sample(c(-1, 1), 1) * sample.int(2 ^ 31 - 1, 1)") 96 | val r = new Random(seed) 97 | val bs = Array.fill(nSamples) { statistic(resample(x, r)) } 98 | scala.util.Sorting.quickSort(bs) 99 | quantile(bs, a / 2) <= truth && truth <= quantile(bs, 1 - a / 2) 100 | ' 101 | } 102 | }) 103 | 104 | coverage.rscala2 <- function(f, n, truth, p1, p2, nSamples, a, nIntervals) { 105 | clusterExport(cluster, c("f", "n", "truth", "p1", "p2", "nSamples", "a"), 106 | envir = environment()) 107 | coverage <- mean(parSapply(cluster, 1:nIntervals, function(i) { 108 | ciContains.rscala2(f, n, truth, p1, p2, nSamples, a) 109 | })) 110 | makeConfidenceInterval(coverage, nIntervals) 111 | } 112 | 113 | 114 | 115 | cat("######## Pure R implementation") 116 | 117 | coverage.pureR <- function(f, n, truth, p1, p2, nSamples, a, nIntervals) { 118 | statistic <- function(x) { 119 | q <- quantile(x, probs = c(p1, p2)) 120 | q[1] / q[2] 121 | } 122 | ciContains.pureR <- function(x) { 123 | samples <- numeric(nSamples) 124 | for ( i in seq_along(samples) ) { 125 | samples[i] <- statistic(sample(x, replace = TRUE)) 126 | } 127 | ci <- quantile(samples, probs = c(a / 2, 1 - a / 2)) 128 | ( ci[1] <= truth ) && ( truth <= ci[2] ) 129 | } 130 | clusterExport(cluster, c("f", "n", "truth", "p1", "p2", "nSamples", "a"), 131 | envir = environment()) 132 | coverage <- mean(parSapply(cluster, 1:nIntervals, function(i) { 133 | ciContains.pureR(f(n)) 134 | })) 135 | makeConfidenceInterval(coverage, nIntervals) 136 | } 137 | 138 | 139 | 140 | cat("######## Rcpp implementation") 141 | 142 | clusterEvalQ(cluster, { 143 | library(Rcpp) 144 | sourceCpp(code = " 145 | #include 146 | using namespace Rcpp; 147 | 148 | double quantile(double *sorted, int length, double p) { 149 | int i = (int) (( length - 1 ) * p); 150 | double delta = ( length - 1 ) * p - i; 151 | return ( 1 - delta ) * sorted[i] + delta * sorted[ i + 1 ]; 152 | } 153 | 154 | int compare_double(const void* a, const void* b) { 155 | double aa = *(double*) a; 156 | double bb = *(double*) b; 157 | if ( aa == bb ) return 0; 158 | return aa < bb ? -1 : 1; 159 | } 160 | 161 | double statistic(double *x, int length, double p1, double p2) { 162 | qsort(x, length, sizeof(double), compare_double); 163 | return quantile(x, length, p1) / quantile(x, length, p2); 164 | } 165 | 166 | double *resample(double *x, int length) { 167 | double *y = (double*) malloc( length * sizeof(double) ); 168 | for ( int i = 0; i < length; i++ ) { 169 | y[i] = x[ (int) (Rf_runif(0, 1) * length) ]; 170 | } 171 | return y; 172 | } 173 | 174 | // [[Rcpp::export]] 175 | bool ciContains(NumericVector data, double truth, 176 | double p1, double p2, int nSamples, double a) { 177 | double *y = (double*) malloc( nSamples * sizeof(double) ); 178 | for ( int i = 0; i < nSamples; i++ ) { 179 | int length = data.size(); 180 | double *z = resample(data.begin(), length); 181 | y[i] = statistic(z, length, p1, p2); 182 | free(z); 183 | } 184 | qsort(y, nSamples, sizeof(double), compare_double); 185 | bool result = ( quantile(y, nSamples, a / 2) <= truth ) && 186 | ( quantile(y, nSamples, 1 - a / 2) >= truth ); 187 | free(y); 188 | return result; 189 | } 190 | ") 191 | }) 192 | 193 | coverage.Rcpp <- function(f, n, truth, p1, p2, nSamples, a, nIntervals) { 194 | clusterExport(cluster, c("f", "n", "truth", "p1", "p2", "nSamples", "a"), 195 | envir = environment()) 196 | coverage <- mean(parSapply(cluster, 1:nIntervals, function(i) { 197 | ciContains(f(n), truth, p1, p2, nSamples, a) 198 | })) 199 | makeConfidenceInterval(coverage, nIntervals) 200 | } 201 | 202 | 203 | 204 | cat("######## Benchmarks") 205 | 206 | system2("hostname") 207 | sessionInfo() 208 | library(microbenchmark) 209 | engine <- function(nSamples, nIntervals, times) microbenchmark( 210 | pureR = coverage.pureR( 211 | rnorm, n, truth, p1, p2, nSamples, alpha, nIntervals), 212 | Rcpp = coverage.Rcpp( 213 | rnorm, n, truth, p1, p2, nSamples, alpha, nIntervals), 214 | rscala1 = coverage.rscala1( 215 | rnorm, n, truth, p1, p2, nSamples, alpha, nIntervals), 216 | rscala2 = coverage.rscala2( 217 | rnorm, n, truth, p1, p2, nSamples, alpha, nIntervals), 218 | times = times) 219 | 220 | engine(nSamples = 10000L, nIntervals = 10000L, times = 10) 221 | -------------------------------------------------------------------------------- /R/rscala/inst/doc/rscala.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/R/rscala/inst/doc/rscala.pdf -------------------------------------------------------------------------------- /R/rscala/inst/java/scala-2.11/rscala.jar: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/R/rscala/inst/java/scala-2.11/rscala.jar -------------------------------------------------------------------------------- /R/rscala/inst/java/scala-2.12/rscala.jar: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/R/rscala/inst/java/scala-2.12/rscala.jar -------------------------------------------------------------------------------- /R/rscala/inst/java/scala-2.13/rscala.jar: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/R/rscala/inst/java/scala-2.13/rscala.jar -------------------------------------------------------------------------------- /R/rscala/inst/rstudio/addins.dcf: -------------------------------------------------------------------------------- 1 | Name: Run scalaSBT() 2 | Description: Runs scalaSBT() 3 | Binding: scalaSBT 4 | Interactive: true 5 | -------------------------------------------------------------------------------- /R/rscala/java/rscala-source.jar: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/R/rscala/java/rscala-source.jar -------------------------------------------------------------------------------- /R/rscala/man/close.rscalaBridge.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/close.R 3 | \name{close.rscalaBridge} 4 | \alias{close.rscalaBridge} 5 | \title{Close a Scala Bridge} 6 | \usage{ 7 | \method{close}{rscalaBridge}(con, ...) 8 | } 9 | \arguments{ 10 | \item{con}{A Scala bridge.} 11 | 12 | \item{...}{Currently ignored.} 13 | } 14 | \value{ 15 | Returns \code{NULL}, invisibly. 16 | } 17 | \description{ 18 | Close a Scala Bridge 19 | } 20 | -------------------------------------------------------------------------------- /R/rscala/man/is.scalaReference.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/is.scalaReference.R 3 | \name{is.scalaReference} 4 | \alias{is.scalaReference} 5 | \title{Test for Scala Reference} 6 | \usage{ 7 | is.scalaReference(x) 8 | } 9 | \arguments{ 10 | \item{x}{An arbitrary R object.} 11 | } 12 | \value{ 13 | Logical indicating whether \code{x} is an rscala reference. 14 | } 15 | \description{ 16 | Test for Scala Reference 17 | } 18 | \examples{ 19 | is.scalaReference(c(1,2)) 20 | 21 | } 22 | -------------------------------------------------------------------------------- /R/rscala/man/plus-.rscalaBridge.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/ops.R 3 | \name{+.rscalaBridge} 4 | \alias{+.rscalaBridge} 5 | \title{Declaration Operator} 6 | \usage{ 7 | \method{+}{rscalaBridge}(bridge, snippet) 8 | } 9 | \arguments{ 10 | \item{bridge}{A Scala bridge.} 11 | 12 | \item{snippet}{String providing a Scala code snippet.} 13 | } 14 | \value{ 15 | Returns \code{NULL}, invisibly. 16 | } 17 | \description{ 18 | This operator compiles and executes a snippet of Scala code \emph{in Scala's 19 | global environment}, where subsequent uses of the same code snippet do 20 | \emph{not} skip the time-consuming compilation step and the return value is 21 | \code{NULL}. As such, this operator is used to define \emph{global} imports, 22 | objects, classes, methods, etc. 23 | } 24 | \examples{ 25 | \donttest{ 26 | s <- scala() 27 | s + ' 28 | import scala.util.Random.nextInt 29 | import scala.math.{Pi, log, exp, sqrt} 30 | val const = -log(sqrt(2*Pi)) 31 | def dnorm(x: Double, mean: Double, sd: Double, logScale: Boolean) = { 32 | val z = ( x - mean ) / sd 33 | val result = const - log(sd) - z * z / 2 34 | if ( logScale ) result else exp(result) 35 | } 36 | ' 37 | s $ const() 38 | s $ nextInt(100L) 39 | s $ dnorm(8, 10, 2, FALSE) 40 | close(s) 41 | } 42 | 43 | } 44 | \seealso{ 45 | \code{\link{*.rscalaBridge}}, \code{\link{^.rscalaBridge}}, 46 | \code{\link{scala}} 47 | } 48 | -------------------------------------------------------------------------------- /R/rscala/man/pow-.rscalaBridge.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/ops.R 3 | \name{^.rscalaBridge} 4 | \alias{^.rscalaBridge} 5 | \title{Evaluation Operator Returning a Reference and Transcompile Operator} 6 | \usage{ 7 | \method{^}{rscalaBridge}(bridge, snippet) 8 | } 9 | \arguments{ 10 | \item{bridge}{A Scala bridge.} 11 | 12 | \item{snippet}{String providing a Scala code snippet.} 13 | } 14 | \value{ 15 | Returns an rscala reference. 16 | } 17 | \description{ 18 | This operator is equivalent to \code{\link{*.rscalaBridge}}, except the 19 | return value is always an rscala reference. This operator also allows (a 20 | small subset of) R code to be transcompiled to Scala code and produces an 21 | rscala reference to an anonymous Scala function. 22 | } 23 | \examples{ 24 | \donttest{ 25 | s <- scala() 26 | x <- s ^ 'new scala.util.Random()' # These two lines ... 27 | x <- s $ .new_scala.util.Random() # ... are equivalent 28 | s(rng=x) * 'rng.nextDouble()' 29 | f <- s ^ function(x=scalaType('Double')) { pi - x } 30 | f$apply(3.14) 31 | s(n=10L, mapper=s ^ function(x=scalaType("Int")) { 2 * x }) * "Array.tabulate(n)(mapper)" 32 | logStdNormalDensity <- s ^ function(x=scalaType("Double"), mean=0.0, sd=1.0) { 33 | variance <- sd^2 34 | -0.5*log(2*pi*variance) - 0.5/variance * (x-mean)^2 35 | } 36 | identical(logStdNormalDensity$apply(1.0), dnorm(1.0, log=TRUE)) 37 | close(s) 38 | } 39 | 40 | } 41 | \seealso{ 42 | \code{\link{*.rscalaBridge}}, \code{\link{+.rscalaBridge}}, 43 | \code{\link{scala}} 44 | } 45 | -------------------------------------------------------------------------------- /R/rscala/man/scala.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/scala.R 3 | \name{scala} 4 | \alias{scala} 5 | \alias{rscala-package} 6 | \title{Instantiate a Scala Bridge} 7 | \usage{ 8 | scala( 9 | JARs = character(), 10 | serialize.output = .Platform$OS.type == "windows", 11 | stdout = TRUE, 12 | stderr = TRUE, 13 | port = 0L, 14 | heap.maximum = NULL, 15 | command.line.arguments = character(0), 16 | debug = FALSE 17 | ) 18 | } 19 | \arguments{ 20 | \item{JARs}{Character vector describing JAR files to include in the 21 | classpath. Elements are some combination of file paths to JARs or package 22 | names which contain embedded JARs. In the case of package names, the 23 | embedded JARs of all packages that recursively depend on, import, or 24 | suggest the specified package are also included.} 25 | 26 | \item{serialize.output}{Logical indicating whether Scala output should be 27 | serialized back to R. This is slower and probably only needed on Windows.} 28 | 29 | \item{stdout}{When \code{serialize.output == FALSE}, this argument influences 30 | where "standard output" results should be sent. \code{TRUE} or \code{""} 31 | sends output to the \R console (although that may not work on Windows). 32 | \code{FALSE} or \code{NULL} discards the output. Otherwise, this is the 33 | name of the file that receives the output.} 34 | 35 | \item{stderr}{Same as \code{stdout}, except influences the "standard error".} 36 | 37 | \item{port}{If \code{0}, two random ports are selected. Otherwise, 38 | \code{port} and \code{port+1} are used to the TCP/IP connections.} 39 | 40 | \item{heap.maximum}{String giving Scala's heap maximum, e.g., "8G" or "512M". 41 | The value here supersedes that from \code{\link{scalaMemory}}. Without this 42 | being set by either \code{\link{scala}} or \code{\link{scalaMemory}}, the 43 | heap maximum will be 90\% of the available RAM.} 44 | 45 | \item{command.line.arguments}{A character vector of extra command line 46 | arguments to pass to the Scala executable, where each element corresponds 47 | to one argument.} 48 | 49 | \item{debug}{(Developer use only.) Logical indicating whether debugging 50 | should be enabled.} 51 | } 52 | \value{ 53 | Returns a Scala bridge. 54 | } 55 | \description{ 56 | This function creates an instance of a Scala bridge. Details on this 57 | function (and the rscala package as a whole) are provided in the package 58 | vignette. The original paper was published in the \emph{Journal of Statistical 59 | Software}. See the reference below. 60 | } 61 | \details{ 62 | Multiple interpreters can be created and each runs independently with its own 63 | memory space. Each interpreter can use multiple threads/cores, but the bridge 64 | between \R and Scala is itself not thread-safe, so multiple \R threads/cores 65 | should not simultaneously access the same bridge. 66 | 67 | Terminate the bridge using \code{\link{close.rscalaBridge}}. 68 | } 69 | \examples{ 70 | \donttest{ 71 | s <- scala() 72 | rng <- s $ .new_scala.util.Random() 73 | rng $ alphanumeric() $ take(15L) $ mkString(',') 74 | s * '2+3' 75 | h <- s(x=2, y=3) ^ 'x+y' 76 | h $ toString() 77 | s(mean=h, sd=2, r=rng) * 'mean + sd * r.nextGaussian()' 78 | close(s) 79 | } 80 | 81 | } 82 | \references{ 83 | {David B. Dahl (2019). "Integration of R and Scala Using rscala." 84 | Journal of Statistical Software, 92:4, 1-18. https://www.jstatsoft.org} 85 | } 86 | \seealso{ 87 | \code{\link{close.rscalaBridge}}, \code{\link{scalaMemory}} 88 | \code{\link{scalaPushRegister}}, \code{\link{scalaPullRegister}} 89 | } 90 | -------------------------------------------------------------------------------- /R/rscala/man/scalaConfig.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/scalaConfig.R 3 | \name{scalaConfig} 4 | \alias{scalaConfig} 5 | \title{Configure Scala and Java} 6 | \usage{ 7 | scalaConfig( 8 | verbose = TRUE, 9 | reconfig = FALSE, 10 | download = character(0), 11 | require.sbt = FALSE 12 | ) 13 | } 14 | \arguments{ 15 | \item{verbose}{Should details of the search for Scala and Java be provided? 16 | Or, if a Scala bridge is provided instead of a logical, the function 17 | returns a list of details associated with the supplied bridge.} 18 | 19 | \item{reconfig}{If \code{TRUE}, the script \code{~/.rscala/config.R} is 20 | rewritten based on a new search for Scala and Java. If \code{FALSE}, the 21 | previous configuration is sourced from the script 22 | \code{~/.rscala/config.R}. If \code{"live"}, a new search is performed, 23 | but the results do not overwrite the previous configuration script. 24 | \code{"offline"} is the same as \code{"live"}, except no software is ever 25 | downloaded. 26 | Finally, the value set here is superceded by the value of the environment 27 | variable \code{RSCALA_RECONFIG}, if it exists.} 28 | 29 | \item{download}{A character vector which may be length-zero or whose elements 30 | are any combination of \code{"java"}, \code{"scala"}, or \code{"sbt"}. Or, 31 | \code{TRUE} denotes all three. The indicated software will be installed in 32 | "~/.rscala".} 33 | 34 | \item{require.sbt}{Should SBT be required, downloading and installing it in 35 | '~/.rscala/sbt' if necessary?} 36 | } 37 | \value{ 38 | Returns a list of details of the Scala and Java binaries. 39 | } 40 | \description{ 41 | This function installs Scala and/or Java in the user's \code{~/.rscala} 42 | directory. 43 | } 44 | \examples{ 45 | \donttest{ 46 | scalaConfig() 47 | } 48 | 49 | } 50 | \references{ 51 | {David B. Dahl (2019). "Integration of R and Scala Using rscala." 52 | Journal of Statistical Software, 92:4, 1-18. https://www.jstatsoft.org} 53 | } 54 | -------------------------------------------------------------------------------- /R/rscala/man/scalaDevelDeployJARs.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/scalaDevelDeployJARs.R 3 | \name{scalaDevelDeployJARs} 4 | \alias{scalaDevelDeployJARs} 5 | \title{Deploy JAR Files into the Package File System} 6 | \usage{ 7 | scalaDevelDeployJARs(name, root, srcJAR, binJARs) 8 | } 9 | \arguments{ 10 | \item{name}{The package name (as a string).} 11 | 12 | \item{root}{The file system path to package root directory (as a string).} 13 | 14 | \item{srcJAR}{The file system path to source JAR file (as a string).} 15 | 16 | \item{binJARs}{A named character vector of file system paths, where each name 17 | is a Scala major version (e.g., \code{"2.13"}.)} 18 | } 19 | \description{ 20 | This function copies the JAR files to the appropriate directories of the R 21 | package source. Specifically, source JAR files go into \code{(PKGHOME)/java} 22 | and binary JAR files go into \code{(PKGHOME)/inst/java/scala-(VERSION)}, 23 | where \code{(PKGHOME)} is the package home and \code{(VERSION)} is the major 24 | Scala version (e.g., 2.13). 25 | } 26 | -------------------------------------------------------------------------------- /R/rscala/man/scalaDisconnect.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/scalaDisconnect.R 3 | \name{scalaDisconnect} 4 | \alias{scalaDisconnect} 5 | \title{Temporarily Disconnect Scala by Closing Connections} 6 | \usage{ 7 | scalaDisconnect(bridge = scalaFindBridge()) 8 | } 9 | \arguments{ 10 | \item{bridge}{A Scala bridge.} 11 | } 12 | \description{ 13 | This function temporarily disconnects a Scala bridge by closing its 14 | associated socket connections. The primary place where this function is used 15 | is at the end of examples of packages that depend on rscala (because, under 16 | some versions of R, "\code{R CMD check --as-cran}" does not permit 17 | connections to persist after an example ends). 18 | } 19 | \examples{ 20 | \donttest{ 21 | showConnections() 22 | s <- scala() 23 | showConnections() # No additional connections yet. 24 | s * "3+4" 25 | showConnections() # Now there are two additional connections. 26 | scalaDisconnect() 27 | showConnections() # The new connections are gone. 28 | s * "3+4" 29 | showConnections() # New connections are established as needed. 30 | close(s) 31 | } 32 | 33 | } 34 | -------------------------------------------------------------------------------- /R/rscala/man/scalaFindBridge.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/scalaFindBridge.R 3 | \name{scalaFindBridge} 4 | \alias{scalaFindBridge} 5 | \title{Find a Scala Bridge} 6 | \usage{ 7 | scalaFindBridge(reference = NULL) 8 | } 9 | \arguments{ 10 | \item{reference}{Either: i. An rscala reference, or ii. \code{NULL} (in which 11 | case the environment path is searched).} 12 | } 13 | \value{ 14 | A Scala bridge. 15 | } 16 | \description{ 17 | This function attempts to find an instance of a Scala bridge based on an 18 | rscala reference or by searching the environment path. 19 | } 20 | -------------------------------------------------------------------------------- /R/rscala/man/scalaLast.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/scalaLast.R 3 | \name{scalaLast} 4 | \alias{scalaLast} 5 | \title{Retrieve the Last Scala Computation} 6 | \usage{ 7 | scalaLast(bridge = scalaFindBridge()) 8 | } 9 | \arguments{ 10 | \item{bridge}{A Scala bridge} 11 | } 12 | \description{ 13 | This function retrieves the last result from the supplied Scala bridge. 14 | } 15 | \examples{ 16 | \donttest{ 17 | s <- scala() 18 | s * "2+3" 19 | scalaLast(s) 20 | close(s) 21 | } 22 | 23 | } 24 | \seealso{ 25 | \code{\link{scalaFindBridge}} 26 | } 27 | -------------------------------------------------------------------------------- /R/rscala/man/scalaLazy.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/scalaLazy.R 3 | \name{scalaLazy} 4 | \alias{scalaLazy} 5 | \title{Lazily Execute Functions on a Scala Bridge} 6 | \usage{ 7 | scalaLazy(functions, bridge = scalaFindBridge()) 8 | } 9 | \arguments{ 10 | \item{functions}{A single function or list of functions. Each function takes 11 | a Scala bridge as its only argument. These functions are called immediately 12 | after the next time the bridge is connected. These functions are where 13 | setup code should go, like \emph{global} imports, objects, classes, 14 | methods, etc. For example, it might equal \code{function(s) { s + 'import 15 | scala.util.Random' }}. \strong{Note} the use of the declaration operator 16 | \code{+} instead of the operators \code{*} or \code{^}.} 17 | 18 | \item{bridge}{A Scala bridge from the \code{scala} function.} 19 | } 20 | \value{ 21 | Returns \code{NULL}, invisibly. 22 | } 23 | \description{ 24 | Lazily Execute Functions on a Scala Bridge 25 | } 26 | \examples{ 27 | \donttest{ 28 | s <- scala() 29 | scalaLazy(function(s) { s + 'import scala.util.Random' }) 30 | s$.new_Random()$nextDouble() 31 | close(s) 32 | } 33 | 34 | } 35 | \seealso{ 36 | \code{\link{scalaFindBridge}} 37 | } 38 | -------------------------------------------------------------------------------- /R/rscala/man/scalaMemory.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/scalaMemory.R 3 | \name{scalaMemory} 4 | \alias{scalaMemory} 5 | \title{Get or Set Memory Available to Scala} 6 | \usage{ 7 | scalaMemory(x) 8 | } 9 | \arguments{ 10 | \item{x}{If the argument is a string (e.g., "8G" or "512M"), the function 11 | sets the default maximum heap size for new instances of Scala bridges 12 | created by the function \code{\link{scala}}. If the argument is missing, 13 | the current default maximum heap size for new instances is returned. Set 14 | the argument to \code{NULL} to disable this global option, and therefore 15 | use \pkg{rscala}'s default. If the argument is a Scala bridge, the 16 | function returns a numeric vector giving the current heap size and the 17 | maximum heap size, in megabytes.} 18 | } 19 | \description{ 20 | Depending on the argument type, this function has several uses related to 21 | memory in Scala. 22 | } 23 | \examples{ 24 | \dontrun{ 25 | scalaMemory("1G") 26 | } 27 | 28 | } 29 | \seealso{ 30 | \code{\link{scala}} 31 | } 32 | -------------------------------------------------------------------------------- /R/rscala/man/scalaPush.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/scalaPull.R, R/scalaPush.R 3 | \name{scalaPull} 4 | \alias{scalaPull} 5 | \alias{scalaPush} 6 | \title{Push and Pull Objects Between R and Scala} 7 | \usage{ 8 | scalaPull(reference, method, ...) 9 | 10 | scalaPush(x, method = "generic", bridge = scalaFindBridge(), ...) 11 | } 12 | \arguments{ 13 | \item{reference}{An rscala reference.} 14 | 15 | \item{method}{A string giving the specific 'push' or 'pull' method to use.} 16 | 17 | \item{...}{Other arguments passed to specialized push and pull functions.} 18 | 19 | \item{x}{An R object.} 20 | 21 | \item{bridge}{A Scala bridge.} 22 | } 23 | \description{ 24 | The push function serializes an R object to Scala and the push function does 25 | the opposite. A couple of built push and pull methods are provided, namely 26 | \code{"generic"} and \code{"list"}. The \code{"generic"} method serializes an 27 | arbitrary R object to an instance of \code{RObject} in Scala. Since the 28 | \code{RObject} merely contains an array of bytes, the \code{RObject} is 29 | really only useful as storage for later unserialization. The \code{"generic"} 30 | method has an optional \code{as.is} argument which is either \code{TRUE} to 31 | cause the list to serialized as a single object or \code{FALSE} to cause each 32 | element of the list to the serialized individually. More methods may be added 33 | using the functions \code{\link{scalaPushRegister}} and 34 | \code{\link{scalaPullRegister}}. 35 | } 36 | \examples{ 37 | \donttest{ 38 | s <- scala() 39 | 40 | s(rn=scalaPush(rnorm),n=5) * 'R.evalD1("\%-(\%-)",rn,n)' 41 | 42 | mtcarsRef <- scalaPush(mtcars, "list") 43 | mtcarsRef$names() 44 | mtcarsRef$mpg() 45 | mtcars2 <- scalaPull(mtcarsRef, "list") 46 | identical(mtcars, mtcars2) 47 | 48 | # Oops, the variable names are bad... 49 | tryCatch(ref <- scalaPush(iris, "list"), error=function(e) e) 50 | 51 | # ... so let's clean up the variable names. 52 | irisCleaned <- iris 53 | names(irisCleaned) <- gsub("\\\\W","_",names(iris)) 54 | irisCleaned$Species <- as.character(iris$Species) 55 | ref2 <- scalaPush(irisCleaned, "list") 56 | scalaType(ref2) 57 | ref2$Sepal_Length() 58 | irisCleaned2 <- scalaPull(ref2,"list") 59 | identical(irisCleaned, irisCleaned2) 60 | 61 | close(s) 62 | } 63 | 64 | } 65 | \seealso{ 66 | \code{\link{scalaPushRegister}}, \code{\link{scalaPullRegister}} 67 | } 68 | -------------------------------------------------------------------------------- /R/rscala/man/scalaPushRegister.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/scalaPushRegister.R 3 | \name{scalaPushRegister} 4 | \alias{scalaPushRegister} 5 | \alias{scalaPullRegister} 6 | \title{Register Functions to Push and Pull Between R and Scala} 7 | \usage{ 8 | scalaPushRegister(pusher, method, bridge = scalaFindBridge()) 9 | 10 | scalaPullRegister(puller, method, bridge = scalaFindBridge()) 11 | } 12 | \arguments{ 13 | \item{pusher}{A function whose first two arguments are as shown in the example below. 14 | Other arguments can be used as additional arguments.} 15 | 16 | \item{method}{A string giving the name of the specific 'push' or 'pull' method.} 17 | 18 | \item{bridge}{A Scala bridge.} 19 | 20 | \item{puller}{A function whose first two arguments are as shown in the example below. 21 | Other arguments can be used as additional arguments.} 22 | } 23 | \description{ 24 | The 'rscala' package provides support for serializing objects between R and Scala. 25 | These registration functions allows 26 | additional, more-specialized push and pull methods to be added. 27 | Package developers may want to call these registration functions in the package's 28 | \code{\link{.onLoad}} function. 29 | } 30 | \examples{ 31 | \donttest{ 32 | s <- scala() 33 | 34 | name <- "Grace" 35 | nameAsRObject <- scalaPush(name,"generic") # Basic serialization 36 | scalaType(nameAsRObject) 37 | identical(name,scalaPull(nameAsRObject,"generic")) 38 | 39 | scalaPush.character <- function(x, bridge) { 40 | if ( is.character(x) && ( length(x) == 1L ) ) bridge(x=x) ^ 'x' 41 | else stop("'x' should be a character vector.") 42 | } 43 | scalaPushRegister(scalaPush.character, "character") 44 | nameAsString <- scalaPush(name, "character", s) # More specific serialization 45 | scalaType(nameAsString) 46 | 47 | scalaPull.character <- function(reference, bridge) { 48 | if ( scalaType(reference) == "String" ) reference$toString() 49 | else stop("'reference' should be a 'String'.") 50 | } 51 | scalaPullRegister(scalaPull.character, "character") 52 | identical(name,scalaPull(nameAsString,"character")) 53 | 54 | close(s) 55 | } 56 | 57 | } 58 | \seealso{ 59 | \code{\link{scalaPush}}, \code{\link{scalaPull}} 60 | } 61 | -------------------------------------------------------------------------------- /R/rscala/man/scalaSBT.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/scalaSBT.R 3 | \name{scalaSBT} 4 | \alias{scalaSBT} 5 | \title{Run SBT and Deploy JAR Files} 6 | \usage{ 7 | scalaSBT( 8 | args = c("+package", "packageSrc"), 9 | copy.to.package = TRUE, 10 | only.if.newer = TRUE 11 | ) 12 | } 13 | \arguments{ 14 | \item{args}{A character vector giving the arguments to be passed to the SBT 15 | command.} 16 | 17 | \item{copy.to.package}{Should the JARs files be copied to the appropriate 18 | directories of the R package source?'} 19 | 20 | \item{only.if.newer}{Should compilation be avoided if it appears Scala code 21 | has not changed?} 22 | } 23 | \value{ 24 | \code{NULL} 25 | } 26 | \description{ 27 | This function helps developers of packages based on rscala. It runs SBT 28 | (Scala Build Tool) to package JAR files and then copy them to the appropriate 29 | directories of the R package source. 30 | } 31 | \details{ 32 | Starting from the current working directory and moving up the file system 33 | hierarchy as needed, this function searches for the directory containing the 34 | file \code{'build.sbt'}, the SBT build file. It temporarily changes the 35 | working directory to this directory. It then runs \code{sbt +package 36 | packageSrc} to package the cross-compiled the Scala code and package the 37 | source code. publish the JAR files locally. Finally, it copies the JAR files 38 | to the appropriate directories of the R package source. Specifically, source 39 | JAR files go into \code{(PKGHOME)/java} and binary JAR files go into 40 | \code{(PKGHOME)/inst/java/scala-(VERSION)}, where \code{(PKGHOME)} is the 41 | package home and \code{(VERSION)} is the major Scala version (e.g., 2.13). It 42 | is assumed that the package home is a subdirectory of the directory 43 | containing the \code{'build.sbt'} file. 44 | 45 | Note that SBT may give weird errors about not being able to download needed 46 | dependences. The issue is that some OpenJDK builds less than version 10 do 47 | not include root certificates. The solution is to either: i. manually 48 | install OpenJDK version 10 or greater, or ii. manually install Oracle's 49 | version of Java. Both are capable with the rscala package. 50 | } 51 | \examples{ 52 | \dontrun{ 53 | scalaSBT() # Working directory is the root of a package based on rscala. 54 | } 55 | 56 | } 57 | -------------------------------------------------------------------------------- /R/rscala/man/scalaType.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/scalaType.R 3 | \docType{data} 4 | \name{scalaType} 5 | \alias{scalaType} 6 | \alias{stI0} 7 | \alias{stD0} 8 | \alias{stL0} 9 | \alias{stR0} 10 | \alias{stS0} 11 | \alias{stI1} 12 | \alias{stD1} 13 | \alias{stL1} 14 | \alias{stR1} 15 | \alias{stS1} 16 | \alias{stI2} 17 | \alias{stD2} 18 | \alias{stL2} 19 | \alias{stR2} 20 | \alias{stS2} 21 | \title{Get or Specify a Scala Type} 22 | \format{ 23 | See 'Value' below. 24 | 25 | An object of class \code{rscalaType} of length 1. 26 | 27 | An object of class \code{rscalaType} of length 1. 28 | 29 | An object of class \code{rscalaType} of length 1. 30 | 31 | An object of class \code{rscalaType} of length 1. 32 | 33 | An object of class \code{rscalaType} of length 1. 34 | 35 | An object of class \code{rscalaType} of length 1. 36 | 37 | An object of class \code{rscalaType} of length 1. 38 | 39 | An object of class \code{rscalaType} of length 1. 40 | 41 | An object of class \code{rscalaType} of length 1. 42 | 43 | An object of class \code{rscalaType} of length 1. 44 | 45 | An object of class \code{rscalaType} of length 1. 46 | 47 | An object of class \code{rscalaType} of length 1. 48 | 49 | An object of class \code{rscalaType} of length 1. 50 | 51 | An object of class \code{rscalaType} of length 1. 52 | 53 | An object of class \code{rscalaType} of length 1. 54 | } 55 | \usage{ 56 | scalaType(type) 57 | 58 | stI0 59 | 60 | stD0 61 | 62 | stL0 63 | 64 | stR0 65 | 66 | stS0 67 | 68 | stI1 69 | 70 | stD1 71 | 72 | stL1 73 | 74 | stR1 75 | 76 | stS1 77 | 78 | stI2 79 | 80 | stD2 81 | 82 | stL2 83 | 84 | stR2 85 | 86 | stS2 87 | } 88 | \arguments{ 89 | \item{type}{An rscala reference or a character vector of length one giving a 90 | Scala type.} 91 | } 92 | \value{ 93 | An object of class \code{rscalaType} whose value is a character 94 | vector of length one indicating a Scala type. 95 | } 96 | \description{ 97 | This function gets the Scala type of an rscala reference. It also, together 98 | with the associated convenience objects, specifies a Scala type for 99 | transcompilation purposes. 100 | } 101 | \details{ 102 | The convenience objects are of the form \code{stXY} (where \code{X} is in 103 | \code{{I, D, L, R, S}} and \code{Y} is in \code{{0, 1, 2}}) as as indicated 104 | below: 105 | 106 | \itemize{ 107 | \item \code{I} corresponds to Scala's \code{Int} and R's \code{integer}. 108 | \item \code{D} corresponds to Scala's \code{Double} and R's \code{double}. 109 | \item \code{L} corresponds to Scala's \code{Boolean} and R's \code{logical}. 110 | \item \code{R} corresponds to Scala's \code{Byte} and R's \code{raw}. 111 | \item \code{S} corresponds to Scala's \code{String} and R's \code{character}. 112 | } 113 | 114 | \itemize{ 115 | \item \code{0} corresponds to a Scala primitive and an R length one vector. 116 | \item \code{1} corresponds to a Scala array and an R vector. 117 | \item \code{2} corresponds to a Scala array of arrays and an R matrix. 118 | } 119 | 120 | For example, \code{stS2} is equivalent to Scala's 121 | \code{scalaType("Array[Array[String]]")} and R's type for 122 | \code{matrix(character())}. Also, \code{stL1} is equivalent to Scala's 123 | \code{scalaType("Boolean")} and R's type for \code{logical(1)}. 124 | } 125 | \examples{ 126 | scalaType("Double") 127 | stD0 128 | scalaType("Array[Byte]") 129 | stR1 130 | scalaType("Array[Array[Int]]") 131 | stI2 132 | 133 | } 134 | \keyword{datasets} 135 | -------------------------------------------------------------------------------- /R/rscala/man/scalaVersionJARs.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/scalaVersionJARs.R 3 | \name{scalaVersionJARs} 4 | \alias{scalaVersionJARs} 5 | \title{JAR Files for Support Scala Versions} 6 | \usage{ 7 | scalaVersionJARs() 8 | } 9 | \value{ 10 | A list whose names correspond to Scala major versions and whose elements are file system paths. 11 | } 12 | \description{ 13 | This function returns a named list whose elements give the file system paths of the JAR files for the supported major versions of Scala. 14 | } 15 | \examples{ 16 | scalaVersionJARs() 17 | 18 | } 19 | -------------------------------------------------------------------------------- /R/rscala/man/times-.rscalaBridge.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/ops.R 3 | \name{*.rscalaBridge} 4 | \alias{*.rscalaBridge} 5 | \title{Evaluation Operator} 6 | \usage{ 7 | \method{*}{rscalaBridge}(bridge, snippet) 8 | } 9 | \arguments{ 10 | \item{bridge}{A Scala bridge.} 11 | 12 | \item{snippet}{String providing a Scala code snippet.} 13 | } 14 | \value{ 15 | Returns a vector or matrix of \R's basic types (if possible) or an 16 | rscala reference (otherwise). 17 | } 18 | \description{ 19 | This operator compiles and executes a snippet of Scala code. All definitions 20 | are \emph{local} to the supplied Scala snippet. Subsequent uses of the same 21 | code snippet skips the time-consuming compilation step. The return value is 22 | a vector or matrix of \R's basic types (if possible) or an rscala reference 23 | (otherwise). 24 | } 25 | \examples{ 26 | \donttest{ 27 | s <- scala() 28 | s * 'scala.util.Random.nextDouble() <= 0.75' 29 | s(mean=10, sd=2.5) * 'mean + sd * scala.util.Random.nextGaussian()' 30 | close(s) 31 | } 32 | 33 | } 34 | \seealso{ 35 | \code{\link{^.rscalaBridge}}, \code{\link{+.rscalaBridge}}, 36 | \code{\link{scala}} 37 | } 38 | -------------------------------------------------------------------------------- /R/rscala/rscala.Rproj: -------------------------------------------------------------------------------- 1 | Version: 1.0 2 | 3 | RestoreWorkspace: No 4 | SaveWorkspace: No 5 | AlwaysSaveHistory: No 6 | 7 | EnableCodeIndexing: Yes 8 | UseSpacesForTab: Yes 9 | NumSpacesForTab: 2 10 | Encoding: UTF-8 11 | 12 | RnwWeave: knitr 13 | LaTeX: pdfLaTeX 14 | 15 | BuildType: Package 16 | PackageUseDevtools: Yes 17 | PackageInstallArgs: --no-multiarch --with-keep.source 18 | PackageBuildArgs: --no-build-vignettes 19 | PackageCheckArgs: --run-donttest 20 | PackageRoxygenize: rd,collate,namespace 21 | 22 | QuitChildProcessesOnExit: Yes 23 | -------------------------------------------------------------------------------- /R/rscala/tests/testthat.R: -------------------------------------------------------------------------------- 1 | # if ( ! isTRUE(tryCatch({rscala::scalaConfig(reconfig="offline")}, error=function(e) TRUE)) ) { 2 | # library(testthat) 3 | # library(rscala) 4 | # test_check("rscala") 5 | # } 6 | -------------------------------------------------------------------------------- /R/rscala/tests/testthat/setup-instance.R: -------------------------------------------------------------------------------- 1 | cat("Starting instance. ********************************\n") 2 | s <- scala(serialize.output=TRUE) 3 | 4 | ## Reduce the ratio of cpu time and elapsed time. 5 | # s2 <- scala(serialize.output=FALSE) 6 | Sys.sleep(5) 7 | 8 | -------------------------------------------------------------------------------- /R/rscala/tests/testthat/teardown-instance.R: -------------------------------------------------------------------------------- 1 | close(s) 2 | # close(s2) 3 | cat("Stopping instance. **************************\n") 4 | -------------------------------------------------------------------------------- /R/rscala/tests/testthat/tests-callbacks.R: -------------------------------------------------------------------------------- 1 | context("callbacks") 2 | 3 | # skip("callbacks") 4 | 5 | x <- 1 6 | 7 | test_that("primitives work in callbacks", { 8 | expect_identical(s(x=x) * 'R.evalI0("%-",x)', as.integer(x)) 9 | expect_identical(s(x=I(x)) * 'R.evalI0("%-",x)', as.integer(x)) 10 | expect_error(s(x=I(x)) * 'R.evalI0("I(%-)",x)', "^Invocation error") 11 | expect_identical(s(x=x) * 'R.evalD0("%-",x)', x) 12 | expect_identical(s(x=I(x)) * 'R.evalD0("%-",x)', x) 13 | expect_error(s(x=I(x)) * 'R.evalD0("I(%-)",x)', "^Invocation error") 14 | expect_identical(s(x=x) * 'R.evalL0("%-",x)', as.logical(x)) 15 | expect_identical(s(x=I(x)) * 'R.evalL0("%-",x)', as.logical(x)) 16 | expect_error(s(x=I(x)) * 'R.evalL0("I(%-)",x)', "^Invocation error") 17 | expect_identical(s(x=x) * 'R.evalR0("%-",x)', as.raw(x)) 18 | expect_identical(s(x=I(x)) * 'R.evalR0("%-",x)', as.raw(x)) 19 | expect_error(s(x=I(x)) * 'R.evalR0("I(%-)",x)', "^Invocation error") 20 | expect_identical(s(x=x) * 'R.evalS0("%-",x)', as.character(x)) 21 | expect_identical(s(x=I(x)) * 'R.evalS0("%-",x)', as.character(x)) 22 | expect_error(s(x=I(x)) * 'R.evalS0("I(%-)",x)', "^Invocation error") 23 | }) 24 | 25 | test_that("length 1 vectors work in callbacks", { 26 | expect_identical(s(x=I(x)) * 'R.evalI1("I(%-)",x)', as.integer(x)) 27 | expect_identical(s(x=I(x)) * 'R.evalD1("I(%-)",x)', x) 28 | expect_identical(s(x=I(x)) * 'R.evalL1("I(%-)",x)', as.logical(x)) 29 | expect_identical(s(x=I(x)) * 'R.evalR1("I(%-)",x)', as.raw(x)) 30 | expect_identical(s(x=I(x)) * 'R.evalS1("I(%-)",x)', as.character(x)) 31 | }) 32 | 33 | x <- c(1,2) 34 | 35 | test_that("length 2 vectors work in callbacks", { 36 | expect_identical(s(x=x) * 'R.evalI1("%-",x)', as.integer(x)) 37 | expect_identical(s(x=x) * 'R.evalD1("%-",x)', x) 38 | expect_identical(s(x=x) * 'R.evalL1("%-",x)', as.logical(x)) 39 | expect_identical(s(x=x) * 'R.evalR1("%-",x)', as.raw(x)) 40 | expect_identical(s(x=x) * 'R.evalS1("%-",x)', as.character(x)) 41 | }) 42 | 43 | x <- matrix(c(0,1),nrow=1) 44 | xi <- x; storage.mode(xi) <- "integer" 45 | xd <- x; storage.mode(xd) <- "double" 46 | xl <- x; storage.mode(xl) <- "logical" 47 | xr <- x; storage.mode(xr) <- "raw" 48 | xc <- x; storage.mode(xc) <- "character" 49 | 50 | test_that("matrices work in callbacks", { 51 | expect_identical(s(x=x) * 'R.evalI2("%-",x)', xi) 52 | expect_identical(s(x=x) * 'R.evalD2("%-",x)', xd) 53 | expect_identical(s(x=x) * 'R.evalL2("%-",x)', xl) 54 | expect_identical(s(x=x) * 'R.evalR2("%-",x)', xr) 55 | expect_identical(s(x=x) * 'R.evalS2("%-",x)', xc) 56 | }) 57 | 58 | test_that("misc. stuff works as expected", { 59 | expect_error(s * 'R.eval("%-",List(1,2))',"^Invocation error") # Unsupported type 60 | }) 61 | 62 | myLittleF <- function() { 63 | x <- 5L 64 | s(x=x) * 'R.eval("a <- %-",x)' 65 | a == x 66 | } 67 | 68 | test_that("we evaluate in the calling R environment.", { 69 | x <- 5L; s(x=x) * 'R.eval("a <- %-",x)'; expect_identical(a,x) 70 | expect_true(myLittleF()) 71 | }) 72 | -------------------------------------------------------------------------------- /R/rscala/tests/testthat/tests-dollar.R: -------------------------------------------------------------------------------- 1 | context("dollar") 2 | 3 | # skip("dollar") 4 | 5 | test_that("references work", { 6 | expect_is(s, "rscalaBridge") 7 | expect_is(s(x=3), "rscalaBridge") 8 | rng <- s$.new_scala.util.Random(); expect_is(rng, "rscalaReference") 9 | expect_lte(rng$nextDouble(),1.0) 10 | expect_gte(rng$nextDouble(),0.0) 11 | expect_gte(rng$nextInt(1L),0L) 12 | expect_lte(rng$nextInt(2L),1L) 13 | expect_true(s(x=s$.null_String()) * "x == null") 14 | expect_true(s(rng=rng,x=rng$.asInstanceOf_AnyRef()) * "x.equals(rng)") 15 | expect_identical(s$.new_String("Hotdog")$toString(),"Hotdog") 16 | expect_identical(s$List(1,2,3,4)$toArray(),c(1,2,3,4)) 17 | expect_is(s$scala.util.Random.nextDouble, "rscalaStub") 18 | expect_type(s$scala.util.Random.nextDouble(), "double") 19 | expect_is(s$.scala.util.Random.nextDouble(), "rscalaReference") 20 | expect_is(s ^ "4", "rscalaReference") 21 | expect_is(s$.Array(1,2,3), "rscalaReference") 22 | expect_identical(s$Array(1,2,3), c(1,2,3)) 23 | expect_null(s + "def nextInt(max: Int) = scala.util.Random.nextInt(max)") 24 | expect_type(s$nextInt(4L),"integer") 25 | nextInt <- s$nextInt; expect_type(nextInt(4L),"integer") 26 | }) 27 | -------------------------------------------------------------------------------- /R/rscala/tests/testthat/tests-lexical-scoping.R: -------------------------------------------------------------------------------- 1 | context("lexical-scoping") 2 | 3 | # skip("lexical-scoping") 4 | 5 | y <- 2 6 | z <- 3 7 | 8 | a1 <- function() { 9 | s(x=1,y) * ' 10 | val z = R.evalD0("z") 11 | x + y*z 12 | ' 13 | } 14 | 15 | a2 <- s(x=1,y) ^ function() { 16 | z <- evalD0("z") 17 | x + y*z 18 | } 19 | 20 | mkNative <- function(x=1) { 21 | y1 <- y 22 | function() { 23 | x + y1*z 24 | } 25 | } 26 | a3 <- mkNative() 27 | 28 | test_that("serialization captures output", { 29 | print(a1()) 30 | expect_identical(a1(), a2()) 31 | expect_identical(a2(), a3()) 32 | z <- 0 33 | print(a1()) 34 | expect_identical(a1(), a2()) 35 | expect_identical(a2(), a3()) 36 | expect_identical(local({ 37 | z <- 29 38 | local({ 39 | z <- 0 40 | local({ 41 | z <- -10 42 | a2() 43 | }) 44 | }) 45 | }),a2()) 46 | 47 | }) 48 | -------------------------------------------------------------------------------- /R/rscala/tests/testthat/tests-matrices.R: -------------------------------------------------------------------------------- 1 | context("matrices") 2 | 3 | # skip("matrices") 4 | 5 | md2by3 <- matrix(c(1,2,3,4,5,6),nrow=2) 6 | mi2by3 <- matrix(as.integer(c(1,2,3,4,5,6)),nrow=2) 7 | ml2by3 <- matrix(as.logical(c(1,0,1,0,1,1)),nrow=2) 8 | mr2by3 <- matrix(as.raw(c(1,2,3,4,5,6)),nrow=2) 9 | mc2by3 <- matrix(as.character(c(1,2,3,4,5,6)),nrow=2) 10 | 11 | test_that("regular matrices transfer to Scala as expected by rows", { 12 | expect_identical(s(m=md2by3) * "m(0)", md2by3[1,]) 13 | expect_identical(s(m=mi2by3) * "m(0)", mi2by3[1,]) 14 | expect_identical(s(m=ml2by3) * "m(0)", ml2by3[1,]) 15 | expect_identical(s(m=mr2by3) * "m(0)", mr2by3[1,]) 16 | expect_identical(s(mc2by3) * "mc2by3(0)", mc2by3[1,]) 17 | expect_identical(s(mc2by3,letters,dummy=pi) * "val dummy2 = dummy; mc2by3(0)", mc2by3[1,]) 18 | }) 19 | 20 | test_that("regular matrices transfer to Scala as expected in full", { 21 | expect_identical(s(m=md2by3) * "m", md2by3) 22 | expect_identical(s(m=mi2by3) * "m", mi2by3) 23 | expect_identical(s(m=ml2by3) * "m", ml2by3) 24 | expect_identical(s(m=mr2by3) * "m", mr2by3) 25 | expect_identical(s(m=mc2by3) * "m", mc2by3) 26 | }) 27 | 28 | md2by1 <- matrix(c(1,2),nrow=2) 29 | mi2by1 <- matrix(as.integer(c(1,2)),nrow=2) 30 | ml2by1 <- matrix(as.logical(c(1,0)),nrow=2) 31 | mr2by1 <- matrix(as.raw(c(1,2)),nrow=2) 32 | mc2by1 <- matrix(as.character(c(1,2)),nrow=2) 33 | 34 | test_that("column vector transfer to Scala as expected by rows", { 35 | expect_identical(s(m=md2by1) * "m(0)", md2by1[1,]) 36 | expect_identical(s(m=mi2by1) * "m(0)", mi2by1[1,]) 37 | expect_identical(s(m=ml2by1) * "m(0)", ml2by1[1,]) 38 | expect_identical(s(m=mr2by1) * "m(0)", mr2by1[1,]) 39 | expect_identical(s(m=mc2by1) * "m(0)", mc2by1[1,]) 40 | }) 41 | 42 | test_that("column vector transfer to Scala as expected in full", { 43 | expect_identical(s(m=md2by1) * "m", md2by1) 44 | expect_identical(s(m=mi2by1) * "m", mi2by1) 45 | expect_identical(s(m=ml2by1) * "m", ml2by1) 46 | expect_identical(s(m=mr2by1) * "m", mr2by1) 47 | expect_identical(s(m=mc2by1) * "m", mc2by1) 48 | }) 49 | 50 | md1by2 <- matrix(c(1,2),nrow=1) 51 | mi1by2 <- matrix(as.integer(c(1,2)),nrow=1) 52 | ml1by2 <- matrix(as.logical(c(1,0)),nrow=1) 53 | mr1by2 <- matrix(as.raw(c(1,2)),nrow=1) 54 | mc1by2 <- matrix(as.character(c(1,2)),nrow=1) 55 | 56 | test_that("row vector transfer to Scala as expected by rows", { 57 | expect_identical(s(m=md1by2) * "m(0)", md1by2[1,]) 58 | expect_identical(s(m=mi1by2) * "m(0)", mi1by2[1,]) 59 | expect_identical(s(m=ml1by2) * "m(0)", ml1by2[1,]) 60 | expect_identical(s(m=mr1by2) * "m(0)", mr1by2[1,]) 61 | expect_identical(s(m=mc1by2) * "m(0)", mc1by2[1,]) 62 | }) 63 | 64 | test_that("row vector transfer to Scala as expected in full", { 65 | expect_identical(s(m=md1by2) * "m", md1by2) 66 | expect_identical(s(m=mi1by2) * "m", mi1by2) 67 | expect_identical(s(m=ml1by2) * "m", ml1by2) 68 | expect_identical(s(m=mr1by2) * "m", mr1by2) 69 | expect_identical(s(m=mc1by2) * "m", mc1by2) 70 | }) 71 | 72 | md2by0 <- matrix(double(),nrow=2,ncol=0) 73 | mi2by0 <- matrix(integer(),nrow=2,ncol=0) 74 | ml2by0 <- matrix(logical(),nrow=2,ncol=0) 75 | mr2by0 <- matrix(raw(),nrow=2,ncol=0) 76 | mc2by0 <- matrix(character(),nrow=2,ncol=0) 77 | 78 | test_that("matrix with no columns and multipe rows transfer to Scala as expected in full", { 79 | expect_identical(s(m=md2by0) * "m", md2by0) 80 | expect_identical(s(m=mi2by0) * "m", mi2by0) 81 | expect_identical(s(m=ml2by0) * "m", ml2by0) 82 | expect_identical(s(m=mr2by0) * "m", mr2by0) 83 | expect_identical(s(m=mc2by0) * "m", mc2by0) 84 | }) 85 | 86 | md1by0 <- matrix(double(),nrow=1,ncol=0) 87 | mi1by0 <- matrix(integer(),nrow=1,ncol=0) 88 | ml1by0 <- matrix(logical(),nrow=1,ncol=0) 89 | mr1by0 <- matrix(raw(),nrow=1,ncol=0) 90 | mc1by0 <- matrix(character(),nrow=1,ncol=0) 91 | 92 | test_that("matrix with no columns and one row transfer to Scala as expected in full", { 93 | expect_identical(s(m=md1by0) * "m", md1by0) 94 | expect_identical(s(m=mi1by0) * "m", mi1by0) 95 | expect_identical(s(m=ml1by0) * "m", ml1by0) 96 | expect_identical(s(m=mr1by0) * "m", mr1by0) 97 | expect_identical(s(m=mc1by0) * "m", mc1by0) 98 | }) 99 | 100 | md0by2 <- matrix(double(),nrow=0,ncol=2) 101 | mi0by2 <- matrix(integer(),nrow=0,ncol=2) 102 | ml0by2 <- matrix(logical(),nrow=0,ncol=2) 103 | mr0by2 <- matrix(raw(),nrow=0,ncol=2) 104 | mc0by2 <- matrix(character(),nrow=0,ncol=2) 105 | 106 | test_that("matrix with no rows transfer to Scala as expected in full", { 107 | expect_error(s(m=md0by2) * "m", "^Number of rows must be at least 1") 108 | expect_error(s(m=mi0by2) * "m", "^Number of rows must be at least 1") 109 | expect_error(s(m=ml0by2) * "m", "^Number of rows must be at least 1") 110 | expect_error(s(m=mr0by2) * "m", "^Number of rows must be at least 1") 111 | expect_error(s(m=mc0by2) * "m", "^Number of rows must be at least 1") 112 | }) 113 | 114 | -------------------------------------------------------------------------------- /R/rscala/tests/testthat/tests-object-serialization.R: -------------------------------------------------------------------------------- 1 | context("object-serialization") 2 | 3 | # skip("object-serialization") 4 | 5 | myExpect <- function(obj,method,...) { 6 | ref <- scalaPush(obj,method,s,...) 7 | newObj <- scalaPull(ref,method) 8 | expect_identical(newObj, obj) 9 | } 10 | 11 | test_that("Basic serialization works", { 12 | myExpect(list(a=1, b=c(TRUE,FALSE), c=I(3.0)), "generic", as.is=TRUE) 13 | myExpect(mtcars,"list") 14 | iris$Species <- as.character(iris$Species) 15 | names(iris) <- gsub("\\W","_",names(iris)) 16 | myExpect(iris,"list") 17 | }) 18 | -------------------------------------------------------------------------------- /R/rscala/tests/testthat/tests-output-serialization.R: -------------------------------------------------------------------------------- 1 | context("output-serialization") 2 | 3 | # skip("output-serialization") 4 | 5 | test_that("serialization captures output", { 6 | # expect_silent(s2 * 'print("Hi")') 7 | expect_output(s * 'print("Hi")', "Hi") 8 | }) 9 | -------------------------------------------------------------------------------- /R/rscala/tests/testthat/tests-recursion.R: -------------------------------------------------------------------------------- 1 | context("recursion") 2 | 3 | # skip("recursion") 4 | 5 | f <- function(counter, verbose=FALSE) { 6 | if ( counter >= 10 ) return(counter) 7 | if ( verbose ) cat("Hello",counter,"from R.\n") 8 | f(s(counter=as.integer(counter[1]), verbose=verbose) * ' 9 | if ( verbose ) println("Hello %s from Scala.".format(counter)) 10 | R.evalI0("%- + 1L",counter) 11 | ', verbose=verbose) 12 | } 13 | 14 | g <- function(counter, verbose=FALSE) { 15 | if ( counter >= 10 ) return(counter) 16 | if ( verbose ) cat("Hello",counter,"from R.\n") 17 | s(counter=as.integer(counter[1]), verbose=verbose) * ' 18 | if ( verbose ) println(s"Hello ${counter} from Scala.") 19 | R.evalI0("g(%-, verbose=%-)", counter+1, verbose) 20 | ' 21 | } 22 | 23 | hh <- function(x, verbose) s(x=as.integer(x[1]), verbose=verbose) * ' 24 | if ( verbose ) println(s"Hello $x from Scala.") 25 | R.evalI0("h(%-, verbose=%-)", x+1, verbose) 26 | ' 27 | 28 | h <- function(counter, verbose=FALSE) { 29 | if ( counter >= 10 ) return(counter) 30 | if ( verbose ) cat("Hello",counter,"from R.\n") 31 | hh(counter, verbose=verbose) 32 | } 33 | 34 | # Note escaped \n because R doesn't have a raw strings 35 | i <- function(x=0L, verbose=FALSE) s(x=as.integer(x[1]), verbose=verbose) * ' 36 | if ( x < 10 ) { 37 | if ( verbose ) println(s"Hello $x from Scala.") 38 | R.evalI0(raw""" 39 | if ( %- ) cat("Hello $x from R.\\n") 40 | i( %-, verbose=%- )""" 41 | , verbose, x+1, verbose) 42 | } else x 43 | ' 44 | 45 | test_that("recursive callbacks work", { 46 | expect_identical(f(0, TRUE), 10L) 47 | expect_identical(g(0, TRUE), 10L) 48 | expect_identical(h(0, TRUE), 10L) 49 | expect_identical(i(0, TRUE), 10L) 50 | expect_identical(s * 'R.evalI0("""s * "3 + 4"""")', 7L) # Make sure everything is still okay! 51 | }) 52 | -------------------------------------------------------------------------------- /R/rscala/tests/testthat/tests-vectors.R: -------------------------------------------------------------------------------- 1 | context("vectors") 2 | 3 | # skip("vectors") 4 | 5 | test_that("length 1 as primitives, bridge without a parameter list", { 6 | expect_identical(s * '0', 0L) 7 | expect_identical(s * '1', 1L) 8 | expect_identical(s * '0.0', 0) 9 | expect_identical(s * '1.0', 1) 10 | expect_identical(s * 'true', TRUE) 11 | expect_identical(s * 'false', FALSE) 12 | expect_identical(s * '0.toByte', as.raw(0)) 13 | expect_identical(s * '1.toByte', as.raw(1)) 14 | expect_identical(s * '"yes"', "yes") 15 | expect_identical(s * '"no"', "no") 16 | }) 17 | 18 | test_that("length 1 as primitives, bridge with a parameter list", { 19 | expect_identical(s(x=0L) * 'x', 0L) 20 | expect_identical(s(x=1L) * 'x', 1L) 21 | expect_identical(s(x=0.0) * 'x', 0) 22 | expect_identical(s(x=1.0) * 'x', 1) 23 | expect_identical(s(x=TRUE) * 'x', TRUE) 24 | expect_identical(s(x=FALSE) * 'x', FALSE) 25 | expect_identical(s(x=as.raw(0)) * 'x', as.raw(0)) 26 | expect_identical(s(x=as.raw(1)) * 'x', as.raw(1)) 27 | expect_identical(s(x="yes") * 'x', "yes") 28 | expect_identical(s(x="no") * 'x', "no") 29 | }) 30 | 31 | test_that("length 1 as vector, bridge with a parameter list", { 32 | expect_identical(s(x=I(0L)) * 'x(0)', 0L) 33 | expect_identical(s(x=I(1L)) * 'x(0)', 1L) 34 | expect_identical(s(x=I(0.0)) * 'x(0)', 0) 35 | expect_identical(s(x=I(1.0)) * 'x(0)', 1) 36 | expect_identical(s(x=I(TRUE)) * 'x(0)', TRUE) 37 | expect_identical(s(x=I(FALSE)) * 'x(0)', FALSE) 38 | expect_identical(s(x=I(as.raw(0))) * 'x(0)', as.raw(0)) 39 | expect_identical(s(x=I(as.raw(1))) * 'x(0)', as.raw(1)) 40 | expect_identical(s(x=I("yes")) * 'x(0)', "yes") 41 | expect_identical(s(x=I("no")) * 'x(0)', "no") 42 | }) 43 | 44 | test_that("length 0 as primitives, bridge with a parameter list", { 45 | expect_identical(s(x=integer()) * 'x', integer()) 46 | expect_identical(s(x=double()) * 'x', double()) 47 | expect_identical(s(x=logical()) * 'x', logical()) 48 | expect_identical(s(x=raw()) * 'x', raw()) 49 | expect_identical(s(x=character()) * 'x', character()) 50 | }) 51 | 52 | test_that("length 3 as primitives, bridge with a parameter list", { 53 | expect_identical(s(x=c(0L,1L,2L)) * 'x', c(0L,1L,2L)) 54 | expect_identical(s(x=c(0,1,2)) * 'x', c(0,1,2)) 55 | expect_identical(s(x=c(TRUE,FALSE,TRUE)) * 'x', c(TRUE,FALSE,TRUE)) 56 | expect_identical(s(x=as.raw(c(0,1,2))) * 'x', as.raw(c(0,1,2))) 57 | expect_identical(s(x=c("yes","no","yes")) * 'x', c("yes","no","yes")) 58 | }) 59 | -------------------------------------------------------------------------------- /R/rscala/vignettes/.install_extras: -------------------------------------------------------------------------------- 1 | bootstrap-coverage.R 2 | -------------------------------------------------------------------------------- /R/rscala/vignettes/build-vignette: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | cd $(dirname $(readlink -f $0)) 4 | 5 | rm -rf ../doc 6 | rm -rf ../inst/doc 7 | 8 | Rscript -e 'devtools::build_vignettes()' 9 | Rscript -e 'tools::compactPDF("../doc/rscala.pdf", gs_quality = "ebook")' 10 | 11 | mv ../doc ../inst/doc 12 | 13 | # R --slave -e 'Sweave("rscala.Rnw")' 14 | # 15 | # pdflatex rscala 16 | # bibtex rscala 17 | # pdflatex rscala 18 | # pdflatex rscala 19 | # pdflatex rscala 20 | 21 | -------------------------------------------------------------------------------- /R/rscala/vignettes/rscala.bib: -------------------------------------------------------------------------------- 1 | \usepackage{url} 2 | 3 | @techreport{scala, 4 | longauthor = {Martin Odersky and Philippe Altherr and Vincent Cremet and Burak Emir and Sebastian Manetha and Stéphane Micheloud and Nikolay Mihaylov and Michel Schinz and Erik Stenman and Matthias Zenger}, 5 | author = {Martin Odersky and others}, 6 | title = {An Overview of the \Scala{} Programming Language}, 7 | institution = {EPFL}, 8 | number = {IC/2004/64}, 9 | address = {Lausanne, Switzerland}, 10 | year = {2004}, 11 | } 12 | 13 | @book{scalabook, 14 | Author = {Martin Odersky and Lex Spoon and Bill Venners}, 15 | Title = {Programming in \Scala{}: {U}pdated for \Scala{} 2.12}, 16 | Publisher = {Artima Press}, 17 | edition = {3rd}, 18 | Year = {2016}, 19 | ISBN = {0981531687}, 20 | } 21 | 22 | @Manual{rscala, 23 | title = {\rscala: Bridge Between \R{} and \Scala{} with Callbacks}, 24 | author = {David B.\ Dahl}, 25 | year = {2018}, 26 | note = {\R{} package version 3.2.1}, 27 | url = {https://CRAN.R-project.org/package=rscala}, 28 | } 29 | 30 | @Manual{R, 31 | title = {\R{}: {A} Language and Environment for Statistical Computing}, 32 | author = {{\R{} Core Team}}, 33 | organization = {\R{} Foundation for Statistical Computing}, 34 | address = {Vienna, Austria}, 35 | year = {2018}, 36 | url = {https://www.R-project.org/}, 37 | } 38 | 39 | @article{spark, 40 | author = {Zaharia, Matei and Xin, Reynold S. and Wendell, Patrick and Das, Tathagata and Armbrust, Michael and Dave, Ankur and Meng, Xiangrui and Rosen, Josh and Venkataraman, Shivaram and Franklin, Michael J. and Ghodsi, Ali and Gonzalez, Joseph and Shenker, Scott and Stoica, Ion}, 41 | title = {Apache \spark{}: A Unified Engine for Big Data Processing}, 42 | journal = {Commun. ACM}, 43 | issue_date = {November 2016}, 44 | volume = {59}, 45 | number = {11}, 46 | month = oct, 47 | year = {2016}, 48 | issn = {0001-0782}, 49 | pages = {56--65}, 50 | numpages = {10}, 51 | doi = {10.1145/2934664}, 52 | acmid = {2934664}, 53 | publisher = {ACM}, 54 | address = {New York, NY, USA}, 55 | } 56 | 57 | @book{9781785280849, 58 | Author = {Md. Rezaul Karim and Sridhar Alla}, 59 | Title = {\Scala{} and \spark{} for Big Data Analytics: Explore the Concepts of Functional Programming, Data Streaming, and Machine Learning}, 60 | Publisher = {Packt Publishing}, 61 | Year = {2017}, 62 | ISBN = {1785280848}, 63 | } 64 | 65 | @book{9781785281372, 66 | Author = {Pascal Bugnion}, 67 | Title = {\Scala{} for Data Science}, 68 | Publisher = {Packt Publishing - ebooks Account}, 69 | Year = {2016}, 70 | ISBN = {9781785281372}, 71 | } 72 | 73 | @book{1785886940, 74 | Author = {Vytautas Jancauskas}, 75 | Title = {Scientific Computing with \Scala{}}, 76 | Publisher = {Packt Publishing - ebooks Account}, 77 | Year = {2016}, 78 | ISBN = {1785886940}, 79 | } 80 | 81 | @book{1783558741, 82 | Author = {Patrick R. Nicolas}, 83 | Title = {\Scala{} for Machine Learning}, 84 | Publisher = {Packt Publishing - ebooks Account}, 85 | Year = {2014}, 86 | ISBN = {1783558741}, 87 | } 88 | 89 | @book{1617292338, 90 | Author = {Avi Pfeffer}, 91 | Title = {Practical Probabilistic Programming}, 92 | Publisher = {Manning Publications}, 93 | Year = {2016}, 94 | ISBN = {1617292338}, 95 | } 96 | 97 | @Article{rcpp, 98 | title = {\Rcpp{}: Seamless \R{} and \Cpp{} Integration}, 99 | author = {Dirk Eddelbuettel and Romain Fran\c{c}ois}, 100 | journal = {Journal of Statistical Software}, 101 | year = {2011}, 102 | volume = {40}, 103 | number = {8}, 104 | pages = {1--18}, 105 | doi = {10.18637/jss.v040.i08}, 106 | } 107 | 108 | @Manual{rJava, 109 | title = {\rJava{}: Low-Level \R{} to \Java{} Interface}, 110 | author = {Simon Urbanek}, 111 | year = {2018}, 112 | note = {\R{} package version 0.9-10}, 113 | url = {https://CRAN.R-project.org/package=rJava}, 114 | } 115 | 116 | @Manual{rserve, 117 | title = {\Rserve{}: Binary \R{} Server}, 118 | author = {Simon Urbanek}, 119 | year = {2013}, 120 | note = {\R{} package version 1.7-3}, 121 | url = {https://CRAN.R-project.org/package=Rserve}, 122 | } 123 | 124 | @article{rcaller, 125 | title={\pkg{RCaller}: A Software Library for Calling \R{} from \Java{}}, 126 | author={Satman, M Hakan}, 127 | journal={British Journal of Mathematics \& Computer Science}, 128 | volume={4}, 129 | number={15}, 130 | pages={2188--2196}, 131 | year={2014} 132 | } 133 | 134 | @Manual{commonsMathSoftware, 135 | title = {\pkg{commonsMath}: {JAR} Files of the {A}pache {C}ommons {M}athematics {L}ibrary}, 136 | author = {{The Apache Software Foundation}}, 137 | year = {2018}, 138 | note = {\R{} package version 1.2}, 139 | url = {https://CRAN.R-project.org/package=commonsMath}, 140 | } 141 | 142 | @Manual{bambooSoftware, 143 | title = {\pkg{bamboo}: Protein Secondary Structure Prediction Using the {B}amboo Method}, 144 | author = {David B.\ Dahl}, 145 | year = {2018}, 146 | note = {\R{} package version 0.9.23}, 147 | url = {https://CRAN.R-project.org/package=bamboo}, 148 | } 149 | 150 | @article{bambooPaper, 151 | author = {Li, Qiwei AND Dahl, David B. AND Vannucci, Marina AND Hyun Joo AND Tsai, Jerry W.}, 152 | journal = {PLOS ONE}, 153 | publisher = {Public Library of Science}, 154 | title = {Bayesian Model of Protein Primary Sequence for Secondary Structure Prediction}, 155 | year = {2014}, 156 | month = {10}, 157 | volume = {9}, 158 | pages = {1-12}, 159 | abstract = {Determining the primary structure (i.e., amino acid sequence) of a protein has become cheaper, faster, and more accurate. Higher order protein structure provides insight into a protein’s function in the cell. Understanding a protein’s secondary structure is a first step towards this goal. Therefore, a number of computational prediction methods have been developed to predict secondary structure from just the primary amino acid sequence. The most successful methods use machine learning approaches that are quite accurate, but do not directly incorporate structural information. As a step towards improving secondary structure reduction given the primary structure, we propose a Bayesian model based on the knob-socket model of protein packing in secondary structure. The method considers the packing influence of residues on the secondary structure determination, including those packed close in space but distant in sequence. By performing an assessment of our method on 2 test sets we show how incorporation of multiple sequence alignment data, similarly to PSIPRED, provides balance and improves the accuracy of the predictions. Software implementing the methods is provided as a web application and a stand-alone implementation.}, 160 | number = {10}, 161 | doi = {10.1371/journal.pone.0109832} 162 | } 163 | 164 | @Manual{sdolsSoftware, 165 | title = {\pkg{sdols}: Summarizing Distributions of Latent Structures}, 166 | author = {David B.\ Dahl}, 167 | year = {2018}, 168 | note = {\R{} package version 1.6}, 169 | url = {https://CRAN.R-project.org/package=sdols}, 170 | } 171 | 172 | @Manual{shallotSoftware, 173 | title = {\pkg{shallot}: Random Partition Distribution Indexed by Pairwise Information}, 174 | author = {David B.\ Dahl}, 175 | year = {2018}, 176 | note = {\R{} package version 0.4.4}, 177 | url = {https://CRAN.R-project.org/package=shallot}, 178 | } 179 | 180 | @article{shallotPaper, 181 | author = {David B.\ Dahl and Ryan Day and Jerry W.\ Tsai}, 182 | title = {Random Partition Distribution Indexed by Pairwise Information}, 183 | journal = {Journal of the American Statistical Association}, 184 | volume = {112}, 185 | number = {518}, 186 | pages = {721-732}, 187 | year = {2017}, 188 | publisher = {Taylor \& Francis}, 189 | doi = {10.1080/01621459.2016.1165103}, 190 | } 191 | 192 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | R/rscala/README.md -------------------------------------------------------------------------------- /benchmarks/all: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | Rb benchmark-compile.R 4 | Rb benchmark-invocation.R 5 | Rb benchmark-large.R 6 | Rb benchmark-references.R 7 | -------------------------------------------------------------------------------- /benchmarks/benchmark-compile-rscala_2.5.3.R: -------------------------------------------------------------------------------- 1 | library(rscala) 2 | library(microbenchmark) 3 | 4 | cat(system2("hostname",stdout=TRUE),"\n",sep="") 5 | scalaInfo() 6 | sessionInfo() 7 | 8 | scala() 9 | nReps <- 100 10 | 11 | ##### 12 | a <- function() s %!% "2056700609" 13 | a() # First-time compilation 14 | 15 | b <- function() s %!% as.character(sample.int(.Machine$integer.max,1)) 16 | b() # Every compilation is new 17 | 18 | microbenchmark( 19 | b(), 20 | a(), 21 | times=nReps 22 | ) 23 | 24 | -------------------------------------------------------------------------------- /benchmarks/benchmark-compile-rscala_2.5.3.Rout: -------------------------------------------------------------------------------- 1 | 2 | R version 3.5.0 (2018-04-23) -- "Joy in Playing" 3 | Copyright (C) 2018 The R Foundation for Statistical Computing 4 | Platform: x86_64-pc-linux-gnu (64-bit) 5 | 6 | R is free software and comes with ABSOLUTELY NO WARRANTY. 7 | You are welcome to redistribute it under certain conditions. 8 | Type 'license()' or 'licence()' for distribution details. 9 | 10 | Natural language support but running in an English locale 11 | 12 | R is a collaborative project with many contributors. 13 | Type 'contributors()' for more information and 14 | 'citation()' on how to cite R or R packages in publications. 15 | 16 | Type 'demo()' for some demos, 'help()' for on-line help, or 17 | 'help.start()' for an HTML browser interface to help. 18 | Type 'q()' to quit R. 19 | 20 | > library(rscala) 21 | > library(microbenchmark) 22 | > 23 | > cat(system2("hostname",stdout=TRUE),"\n",sep="") 24 | sidon 25 | > scalaInfo() 26 | $cmd 27 | [1] "/home/dahl/local/scala/scala/scala-2.12.3/bin/scala" 28 | 29 | $home 30 | [1] "/home/dahl/local/scala/scala/scala-2.12.3" 31 | 32 | $version 33 | [1] "2.12.3" 34 | 35 | $major.release 36 | [1] "2.12" 37 | 38 | > sessionInfo() 39 | R version 3.5.0 (2018-04-23) 40 | Platform: x86_64-pc-linux-gnu (64-bit) 41 | Running under: Ubuntu 16.04.4 LTS 42 | 43 | Matrix products: default 44 | BLAS: /usr/lib/libblas/libblas.so.3.6.0 45 | LAPACK: /usr/lib/lapack/liblapack.so.3.6.0 46 | 47 | locale: 48 | [1] LC_CTYPE=en_US.UTF-8 LC_NUMERIC=C 49 | [3] LC_TIME=en_US.UTF-8 LC_COLLATE=en_US.UTF-8 50 | [5] LC_MONETARY=en_US.UTF-8 LC_MESSAGES=en_US.UTF-8 51 | [7] LC_PAPER=en_US.UTF-8 LC_NAME=C 52 | [9] LC_ADDRESS=C LC_TELEPHONE=C 53 | [11] LC_MEASUREMENT=en_US.UTF-8 LC_IDENTIFICATION=C 54 | 55 | attached base packages: 56 | [1] stats graphics grDevices utils datasets methods base 57 | 58 | other attached packages: 59 | [1] microbenchmark_1.4-4 rscala_2.5.3 60 | 61 | loaded via a namespace (and not attached): 62 | [1] compiler_3.5.0 63 | > 64 | > scala() 65 | > nReps <- 100 66 | > 67 | > ##### 68 | > a <- function() s %!% "2056700609" 69 | > a() # First-time compilation 70 | [1] 2056700609 71 | > 72 | > b <- function() s %!% as.character(sample.int(.Machine$integer.max,1)) 73 | > b() # Every compilation is new 74 | [1] 944229090 75 | > 76 | > microbenchmark( 77 | + b(), 78 | + a(), 79 | + times=nReps 80 | + ) 81 | Unit: microseconds 82 | expr min lq mean median uq max neval 83 | b() 109748.754 138338.3 182585.6930 166595.0105 206634.6090 401910.292 100 84 | a() 433.563 597.0 800.5838 751.6345 951.9155 2485.805 100 85 | > 86 | > 87 | > proc.time() 88 | user system elapsed 89 | 0.523 0.214 24.831 90 | -------------------------------------------------------------------------------- /benchmarks/benchmark-compile.R: -------------------------------------------------------------------------------- 1 | library(rscala) 2 | library(microbenchmark) 3 | 4 | cat(system2("hostname",stdout=TRUE),"\n",sep="") 5 | scalaConfig() 6 | sessionInfo() 7 | 8 | s <- scala() 9 | nReps <- 100 10 | 11 | ##### 12 | s * 2056700609 # First-time compilation 13 | 14 | microbenchmark( 15 | s * sample.int(.Machine$integer.max,1), 16 | s * 2056700609, 17 | times=nReps 18 | ) 19 | 20 | -------------------------------------------------------------------------------- /benchmarks/benchmark-compile.Rout: -------------------------------------------------------------------------------- 1 | 2 | R Under development (unstable) (2023-01-21 r83656) -- "Unsuffered Consequences" 3 | Copyright (C) 2023 The R Foundation for Statistical Computing 4 | Platform: x86_64-pc-linux-gnu (64-bit) 5 | 6 | R is free software and comes with ABSOLUTELY NO WARRANTY. 7 | You are welcome to redistribute it under certain conditions. 8 | Type 'license()' or 'licence()' for distribution details. 9 | 10 | Natural language support but running in an English locale 11 | 12 | R is a collaborative project with many contributors. 13 | Type 'contributors()' for more information and 14 | 'citation()' on how to cite R or R packages in publications. 15 | 16 | Type 'demo()' for some demos, 'help()' for on-line help, or 17 | 'help.start()' for an HTML browser interface to help. 18 | Type 'q()' to quit R. 19 | 20 | > library(rscala) 21 | > library(microbenchmark) 22 | > 23 | > cat(system2("hostname",stdout=TRUE),"\n",sep="") 24 | abish 25 | > scalaConfig() 26 | 27 | Read configuration file from rscala home: /home/dahl/.rscala/config.R 28 | 29 | $format 30 | [1] 4 31 | 32 | $scalaHome 33 | [1] "/home/dahl/.rscala/scala" 34 | 35 | $scalaCmd 36 | [1] "/home/dahl/.rscala/scala/bin/scala" 37 | 38 | $scalaMajorVersion 39 | [1] "2.13" 40 | 41 | $scalaFullVersion 42 | [1] "2.13.10" 43 | 44 | $javaHome 45 | [1] "/home/dahl/.rscala/java/jre" 46 | 47 | $javaCmd 48 | [1] "/home/dahl/.rscala/java/bin/java" 49 | 50 | $javaMajorVersion 51 | [1] 8 52 | 53 | $javaArchitecture 54 | [1] 64 55 | 56 | $sbtCmd 57 | [1] "/home/dahl/.rscala/sbt/bin/sbt" 58 | 59 | > sessionInfo() 60 | R Under development (unstable) (2023-01-21 r83656) 61 | Platform: x86_64-pc-linux-gnu (64-bit) 62 | Running under: Pop!_OS 22.04 LTS 63 | 64 | Matrix products: default 65 | BLAS/LAPACK: /usr/lib/x86_64-linux-gnu/openblas-pthread/libopenblasp-r0.3.20.so; LAPACK version 3.10.0 66 | 67 | locale: 68 | [1] LC_CTYPE=en_US.UTF-8 LC_NUMERIC=C 69 | [3] LC_TIME=en_US.UTF-8 LC_COLLATE=en_US.UTF-8 70 | [5] LC_MONETARY=en_US.UTF-8 LC_MESSAGES=en_US.UTF-8 71 | [7] LC_PAPER=en_US.UTF-8 LC_NAME=C 72 | [9] LC_ADDRESS=C LC_TELEPHONE=C 73 | [11] LC_MEASUREMENT=en_US.UTF-8 LC_IDENTIFICATION=C 74 | 75 | time zone: America/Denver 76 | tzcode source: system (glibc) 77 | 78 | attached base packages: 79 | [1] stats graphics grDevices utils datasets methods base 80 | 81 | other attached packages: 82 | [1] microbenchmark_1.4.9 rscala_3.2.20 83 | 84 | loaded via a namespace (and not attached): 85 | [1] compiler_4.3.0 tools_4.3.0 86 | > 87 | > s <- scala() 88 | > nReps <- 100 89 | > 90 | > ##### 91 | > s * 2056700609 # First-time compilation 92 | [1] 2056700609 93 | > 94 | > microbenchmark( 95 | + s * sample.int(.Machine$integer.max,1), 96 | + s * 2056700609, 97 | + times=nReps 98 | + ) 99 | Unit: microseconds 100 | expr min lq mean 101 | s * sample.int(.Machine$integer.max, 1) 53517.259 63427.3795 94886.8953 102 | s * 2056700609 95.443 169.3415 249.5255 103 | median uq max neval 104 | 79523.421 122593.0565 270725.840 100 105 | 234.176 305.1555 648.316 100 106 | > 107 | > 108 | > proc.time() 109 | user system elapsed 110 | 0.481 1.082 12.666 111 | -------------------------------------------------------------------------------- /benchmarks/benchmark-invocation-rscala_2.5.3.R: -------------------------------------------------------------------------------- 1 | library(rscala) 2 | library(microbenchmark) 3 | 4 | cat(system2("hostname",stdout=TRUE),"\n",sep="") 5 | scalaInfo() 6 | sessionInfo() 7 | 8 | openAndClose <- function() { 9 | scala() 10 | s %~% "3" 11 | close(s) 12 | } 13 | 14 | microbenchmark( 15 | openAndClose(), 16 | times=10 17 | ) 18 | -------------------------------------------------------------------------------- /benchmarks/benchmark-invocation-rscala_2.5.3.Rout: -------------------------------------------------------------------------------- 1 | 2 | R version 3.5.0 (2018-04-23) -- "Joy in Playing" 3 | Copyright (C) 2018 The R Foundation for Statistical Computing 4 | Platform: x86_64-pc-linux-gnu (64-bit) 5 | 6 | R is free software and comes with ABSOLUTELY NO WARRANTY. 7 | You are welcome to redistribute it under certain conditions. 8 | Type 'license()' or 'licence()' for distribution details. 9 | 10 | Natural language support but running in an English locale 11 | 12 | R is a collaborative project with many contributors. 13 | Type 'contributors()' for more information and 14 | 'citation()' on how to cite R or R packages in publications. 15 | 16 | Type 'demo()' for some demos, 'help()' for on-line help, or 17 | 'help.start()' for an HTML browser interface to help. 18 | Type 'q()' to quit R. 19 | 20 | > library(rscala) 21 | > library(microbenchmark) 22 | > 23 | > cat(system2("hostname",stdout=TRUE),"\n",sep="") 24 | sidon 25 | > scalaInfo() 26 | $cmd 27 | [1] "/home/dahl/local/scala/scala/scala-2.12.3/bin/scala" 28 | 29 | $home 30 | [1] "/home/dahl/local/scala/scala/scala-2.12.3" 31 | 32 | $version 33 | [1] "2.12.3" 34 | 35 | $major.release 36 | [1] "2.12" 37 | 38 | > sessionInfo() 39 | R version 3.5.0 (2018-04-23) 40 | Platform: x86_64-pc-linux-gnu (64-bit) 41 | Running under: Ubuntu 16.04.4 LTS 42 | 43 | Matrix products: default 44 | BLAS: /usr/lib/libblas/libblas.so.3.6.0 45 | LAPACK: /usr/lib/lapack/liblapack.so.3.6.0 46 | 47 | locale: 48 | [1] LC_CTYPE=en_US.UTF-8 LC_NUMERIC=C 49 | [3] LC_TIME=en_US.UTF-8 LC_COLLATE=en_US.UTF-8 50 | [5] LC_MONETARY=en_US.UTF-8 LC_MESSAGES=en_US.UTF-8 51 | [7] LC_PAPER=en_US.UTF-8 LC_NAME=C 52 | [9] LC_ADDRESS=C LC_TELEPHONE=C 53 | [11] LC_MEASUREMENT=en_US.UTF-8 LC_IDENTIFICATION=C 54 | 55 | attached base packages: 56 | [1] stats graphics grDevices utils datasets methods base 57 | 58 | other attached packages: 59 | [1] microbenchmark_1.4-4 rscala_2.5.3 60 | 61 | loaded via a namespace (and not attached): 62 | [1] compiler_3.5.0 63 | > 64 | > openAndClose <- function() { 65 | + scala() 66 | + s %~% "3" 67 | + close(s) 68 | + } 69 | > 70 | > microbenchmark( 71 | + openAndClose(), 72 | + times=10 73 | + ) 74 | Unit: seconds 75 | expr min lq mean median uq max neval 76 | openAndClose() 5.027311 5.088004 5.179093 5.181104 5.234228 5.343217 10 77 | > 78 | > proc.time() 79 | user system elapsed 80 | 0.779 0.299 52.164 81 | -------------------------------------------------------------------------------- /benchmarks/benchmark-invocation.R: -------------------------------------------------------------------------------- 1 | library(rscala) 2 | library(microbenchmark) 3 | 4 | cat(system2("hostname",stdout=TRUE),"\n",sep="") 5 | scalaConfig() 6 | sessionInfo() 7 | 8 | openAndClose <- function() { 9 | s <- scala() 10 | s * "3" 11 | close(s) 12 | } 13 | 14 | microbenchmark( 15 | openAndClose(), 16 | times=25 17 | ) 18 | -------------------------------------------------------------------------------- /benchmarks/benchmark-invocation.Rout: -------------------------------------------------------------------------------- 1 | 2 | R Under development (unstable) (2023-01-21 r83656) -- "Unsuffered Consequences" 3 | Copyright (C) 2023 The R Foundation for Statistical Computing 4 | Platform: x86_64-pc-linux-gnu (64-bit) 5 | 6 | R is free software and comes with ABSOLUTELY NO WARRANTY. 7 | You are welcome to redistribute it under certain conditions. 8 | Type 'license()' or 'licence()' for distribution details. 9 | 10 | Natural language support but running in an English locale 11 | 12 | R is a collaborative project with many contributors. 13 | Type 'contributors()' for more information and 14 | 'citation()' on how to cite R or R packages in publications. 15 | 16 | Type 'demo()' for some demos, 'help()' for on-line help, or 17 | 'help.start()' for an HTML browser interface to help. 18 | Type 'q()' to quit R. 19 | 20 | > library(rscala) 21 | > library(microbenchmark) 22 | > 23 | > cat(system2("hostname",stdout=TRUE),"\n",sep="") 24 | abish 25 | > scalaConfig() 26 | 27 | Read configuration file from rscala home: /home/dahl/.rscala/config.R 28 | 29 | $format 30 | [1] 4 31 | 32 | $scalaHome 33 | [1] "/home/dahl/.rscala/scala" 34 | 35 | $scalaCmd 36 | [1] "/home/dahl/.rscala/scala/bin/scala" 37 | 38 | $scalaMajorVersion 39 | [1] "2.13" 40 | 41 | $scalaFullVersion 42 | [1] "2.13.10" 43 | 44 | $javaHome 45 | [1] "/home/dahl/.rscala/java/jre" 46 | 47 | $javaCmd 48 | [1] "/home/dahl/.rscala/java/bin/java" 49 | 50 | $javaMajorVersion 51 | [1] 8 52 | 53 | $javaArchitecture 54 | [1] 64 55 | 56 | $sbtCmd 57 | [1] "/home/dahl/.rscala/sbt/bin/sbt" 58 | 59 | > sessionInfo() 60 | R Under development (unstable) (2023-01-21 r83656) 61 | Platform: x86_64-pc-linux-gnu (64-bit) 62 | Running under: Pop!_OS 22.04 LTS 63 | 64 | Matrix products: default 65 | BLAS/LAPACK: /usr/lib/x86_64-linux-gnu/openblas-pthread/libopenblasp-r0.3.20.so; LAPACK version 3.10.0 66 | 67 | locale: 68 | [1] LC_CTYPE=en_US.UTF-8 LC_NUMERIC=C 69 | [3] LC_TIME=en_US.UTF-8 LC_COLLATE=en_US.UTF-8 70 | [5] LC_MONETARY=en_US.UTF-8 LC_MESSAGES=en_US.UTF-8 71 | [7] LC_PAPER=en_US.UTF-8 LC_NAME=C 72 | [9] LC_ADDRESS=C LC_TELEPHONE=C 73 | [11] LC_MEASUREMENT=en_US.UTF-8 LC_IDENTIFICATION=C 74 | 75 | time zone: America/Denver 76 | tzcode source: system (glibc) 77 | 78 | attached base packages: 79 | [1] stats graphics grDevices utils datasets methods base 80 | 81 | other attached packages: 82 | [1] microbenchmark_1.4.9 rscala_3.2.20 83 | 84 | loaded via a namespace (and not attached): 85 | [1] compiler_4.3.0 tools_4.3.0 86 | > 87 | > openAndClose <- function() { 88 | + s <- scala() 89 | + s * "3" 90 | + close(s) 91 | + } 92 | > 93 | > microbenchmark( 94 | + openAndClose(), 95 | + times=25 96 | + ) 97 | Unit: seconds 98 | expr min lq mean median uq max neval 99 | openAndClose() 2.820229 2.951521 3.112698 3.017634 3.237664 3.589079 25 100 | > 101 | > proc.time() 102 | user system elapsed 103 | 0.812 1.243 78.058 104 | -------------------------------------------------------------------------------- /benchmarks/benchmark-large-rscala_2.5.3.R: -------------------------------------------------------------------------------- 1 | library(rscala) 2 | library(microbenchmark) 3 | 4 | cat(system2("hostname",stdout=TRUE),"\n",sep="") 5 | scalaInfo() 6 | sessionInfo() 7 | 8 | scala(heap.maximum="14090M") 9 | nReps <- 100 10 | 11 | ##### 12 | 13 | big <- rnorm(10000000) 14 | a <- function(x) s %.!% 'x' 15 | b <- function(x) s %!% 'x' 16 | invisible(a(big)) 17 | invisible(b(big)) 18 | 19 | microbenchmark( 20 | a(big), 21 | b(big), 22 | times=nReps 23 | ) 24 | 25 | s %~% "true" # Is everything still okay? 26 | 27 | -------------------------------------------------------------------------------- /benchmarks/benchmark-large-rscala_2.5.3.Rout: -------------------------------------------------------------------------------- 1 | 2 | R version 3.5.0 (2018-04-23) -- "Joy in Playing" 3 | Copyright (C) 2018 The R Foundation for Statistical Computing 4 | Platform: x86_64-pc-linux-gnu (64-bit) 5 | 6 | R is free software and comes with ABSOLUTELY NO WARRANTY. 7 | You are welcome to redistribute it under certain conditions. 8 | Type 'license()' or 'licence()' for distribution details. 9 | 10 | Natural language support but running in an English locale 11 | 12 | R is a collaborative project with many contributors. 13 | Type 'contributors()' for more information and 14 | 'citation()' on how to cite R or R packages in publications. 15 | 16 | Type 'demo()' for some demos, 'help()' for on-line help, or 17 | 'help.start()' for an HTML browser interface to help. 18 | Type 'q()' to quit R. 19 | 20 | > library(rscala) 21 | > library(microbenchmark) 22 | > 23 | > cat(system2("hostname",stdout=TRUE),"\n",sep="") 24 | sidon 25 | > scalaInfo() 26 | $cmd 27 | [1] "/home/dahl/local/scala/scala/scala-2.12.3/bin/scala" 28 | 29 | $home 30 | [1] "/home/dahl/local/scala/scala/scala-2.12.3" 31 | 32 | $version 33 | [1] "2.12.3" 34 | 35 | $major.release 36 | [1] "2.12" 37 | 38 | > sessionInfo() 39 | R version 3.5.0 (2018-04-23) 40 | Platform: x86_64-pc-linux-gnu (64-bit) 41 | Running under: Ubuntu 16.04.4 LTS 42 | 43 | Matrix products: default 44 | BLAS: /usr/lib/libblas/libblas.so.3.6.0 45 | LAPACK: /usr/lib/lapack/liblapack.so.3.6.0 46 | 47 | locale: 48 | [1] LC_CTYPE=en_US.UTF-8 LC_NUMERIC=C 49 | [3] LC_TIME=en_US.UTF-8 LC_COLLATE=en_US.UTF-8 50 | [5] LC_MONETARY=en_US.UTF-8 LC_MESSAGES=en_US.UTF-8 51 | [7] LC_PAPER=en_US.UTF-8 LC_NAME=C 52 | [9] LC_ADDRESS=C LC_TELEPHONE=C 53 | [11] LC_MEASUREMENT=en_US.UTF-8 LC_IDENTIFICATION=C 54 | 55 | attached base packages: 56 | [1] stats graphics grDevices utils datasets methods base 57 | 58 | other attached packages: 59 | [1] microbenchmark_1.4-4 rscala_2.5.3 60 | 61 | loaded via a namespace (and not attached): 62 | [1] compiler_3.5.0 63 | > 64 | > scala(heap.maximum="14090M") 65 | > nReps <- 100 66 | > 67 | > ##### 68 | > 69 | > big <- rnorm(10000000) 70 | > a <- function(x) s %.!% 'x' 71 | > b <- function(x) s %!% 'x' 72 | > invisible(a(big)) 73 | > invisible(b(big)) 74 | > 75 | > microbenchmark( 76 | + a(big), 77 | + b(big), 78 | + times=nReps 79 | + ) 80 | Unit: milliseconds 81 | expr min lq mean median uq max neval 82 | a(big) 95.22489 97.41297 106.8329 99.16171 104.1442 222.7237 100 83 | b(big) 235.88799 240.04200 270.6718 244.88655 283.5911 466.0370 100 84 | > 85 | > s %~% "true" # Is everything still okay? 86 | [1] TRUE 87 | > 88 | > 89 | > proc.time() 90 | user system elapsed 91 | 14.229 13.755 44.262 92 | -------------------------------------------------------------------------------- /benchmarks/benchmark-large.R: -------------------------------------------------------------------------------- 1 | library(rscala) 2 | library(microbenchmark) 3 | 4 | cat(system2("hostname",stdout=TRUE),"\n",sep="") 5 | scalaConfig() 6 | sessionInfo() 7 | 8 | s <- scala() 9 | nReps <- 100 10 | 11 | ##### 12 | 13 | big <- rnorm(10000000) 14 | microbenchmark( 15 | s(x=big) ^ 'x', 16 | s(x=big) * 'x', 17 | times=nReps 18 | ) 19 | 20 | s * "true" # Is everything still okay? 21 | 22 | -------------------------------------------------------------------------------- /benchmarks/benchmark-large.Rout: -------------------------------------------------------------------------------- 1 | 2 | R Under development (unstable) (2023-01-21 r83656) -- "Unsuffered Consequences" 3 | Copyright (C) 2023 The R Foundation for Statistical Computing 4 | Platform: x86_64-pc-linux-gnu (64-bit) 5 | 6 | R is free software and comes with ABSOLUTELY NO WARRANTY. 7 | You are welcome to redistribute it under certain conditions. 8 | Type 'license()' or 'licence()' for distribution details. 9 | 10 | Natural language support but running in an English locale 11 | 12 | R is a collaborative project with many contributors. 13 | Type 'contributors()' for more information and 14 | 'citation()' on how to cite R or R packages in publications. 15 | 16 | Type 'demo()' for some demos, 'help()' for on-line help, or 17 | 'help.start()' for an HTML browser interface to help. 18 | Type 'q()' to quit R. 19 | 20 | > library(rscala) 21 | > library(microbenchmark) 22 | > 23 | > cat(system2("hostname",stdout=TRUE),"\n",sep="") 24 | abish 25 | > scalaConfig() 26 | 27 | Read configuration file from rscala home: /home/dahl/.rscala/config.R 28 | 29 | $format 30 | [1] 4 31 | 32 | $scalaHome 33 | [1] "/home/dahl/.rscala/scala" 34 | 35 | $scalaCmd 36 | [1] "/home/dahl/.rscala/scala/bin/scala" 37 | 38 | $scalaMajorVersion 39 | [1] "2.13" 40 | 41 | $scalaFullVersion 42 | [1] "2.13.10" 43 | 44 | $javaHome 45 | [1] "/home/dahl/.rscala/java/jre" 46 | 47 | $javaCmd 48 | [1] "/home/dahl/.rscala/java/bin/java" 49 | 50 | $javaMajorVersion 51 | [1] 8 52 | 53 | $javaArchitecture 54 | [1] 64 55 | 56 | $sbtCmd 57 | [1] "/home/dahl/.rscala/sbt/bin/sbt" 58 | 59 | > sessionInfo() 60 | R Under development (unstable) (2023-01-21 r83656) 61 | Platform: x86_64-pc-linux-gnu (64-bit) 62 | Running under: Pop!_OS 22.04 LTS 63 | 64 | Matrix products: default 65 | BLAS/LAPACK: /usr/lib/x86_64-linux-gnu/openblas-pthread/libopenblasp-r0.3.20.so; LAPACK version 3.10.0 66 | 67 | locale: 68 | [1] LC_CTYPE=en_US.UTF-8 LC_NUMERIC=C 69 | [3] LC_TIME=en_US.UTF-8 LC_COLLATE=en_US.UTF-8 70 | [5] LC_MONETARY=en_US.UTF-8 LC_MESSAGES=en_US.UTF-8 71 | [7] LC_PAPER=en_US.UTF-8 LC_NAME=C 72 | [9] LC_ADDRESS=C LC_TELEPHONE=C 73 | [11] LC_MEASUREMENT=en_US.UTF-8 LC_IDENTIFICATION=C 74 | 75 | time zone: America/Denver 76 | tzcode source: system (glibc) 77 | 78 | attached base packages: 79 | [1] stats graphics grDevices utils datasets methods base 80 | 81 | other attached packages: 82 | [1] microbenchmark_1.4.9 rscala_3.2.20 83 | 84 | loaded via a namespace (and not attached): 85 | [1] compiler_4.3.0 tools_4.3.0 86 | > 87 | > s <- scala() 88 | > nReps <- 100 89 | > 90 | > ##### 91 | > 92 | > big <- rnorm(10000000) 93 | > microbenchmark( 94 | + s(x=big) ^ 'x', 95 | + s(x=big) * 'x', 96 | + times=nReps 97 | + ) 98 | Unit: milliseconds 99 | expr min lq mean median uq max 100 | s(x = big)^"x" 114.5183 120.4203 135.3956 123.163 125.108 722.7929 101 | s(x = big) * "x" 7480.4226 7629.0354 7905.8090 7690.537 7817.965 12090.7945 102 | neval 103 | 100 104 | 100 105 | > 106 | > s * "true" # Is everything still okay? 107 | [1] TRUE 108 | > 109 | > 110 | > proc.time() 111 | user system elapsed 112 | 68.290 613.525 805.350 113 | -------------------------------------------------------------------------------- /benchmarks/benchmark-references-rscala_2.5.3.R: -------------------------------------------------------------------------------- 1 | library(rscala) 2 | library(microbenchmark) 3 | 4 | cat(system2("hostname",stdout=TRUE),"\n",sep="") 5 | scalaInfo() 6 | sessionInfo() 7 | 8 | scala() 9 | nReps <- 10000 10 | 11 | ##### 12 | 13 | rng <- s$.scala.util.Random$new() 14 | rng$nextInt() # First-time compilation 15 | rng$nextInt(1L) # First-time compilation 16 | nextInt <- rng$nextInt 17 | nextInt() # Alreary compiled 18 | nextInt(1L) # Alreary compiled 19 | 20 | a <- function(rng) s %!% 'rng.nextInt()' 21 | b <- function(rng) s %.!% 'rng.nextInt()' 22 | a(rng) 23 | b(rng) 24 | 25 | microbenchmark( 26 | b(rng), 27 | a(rng), 28 | rng$nextInt(.AS.REFERENCE=TRUE), 29 | rng$nextInt(), 30 | nextInt(), 31 | rng$nextInt(100L,.AS.REFERENCE=TRUE), 32 | rng$nextInt(100L), 33 | nextInt(100L), 34 | times=nReps 35 | ) 36 | 37 | 38 | -------------------------------------------------------------------------------- /benchmarks/benchmark-references-rscala_2.5.3.Rout: -------------------------------------------------------------------------------- 1 | 2 | R version 3.5.0 (2018-04-23) -- "Joy in Playing" 3 | Copyright (C) 2018 The R Foundation for Statistical Computing 4 | Platform: x86_64-pc-linux-gnu (64-bit) 5 | 6 | R is free software and comes with ABSOLUTELY NO WARRANTY. 7 | You are welcome to redistribute it under certain conditions. 8 | Type 'license()' or 'licence()' for distribution details. 9 | 10 | Natural language support but running in an English locale 11 | 12 | R is a collaborative project with many contributors. 13 | Type 'contributors()' for more information and 14 | 'citation()' on how to cite R or R packages in publications. 15 | 16 | Type 'demo()' for some demos, 'help()' for on-line help, or 17 | 'help.start()' for an HTML browser interface to help. 18 | Type 'q()' to quit R. 19 | 20 | > library(rscala) 21 | > library(microbenchmark) 22 | > 23 | > cat(system2("hostname",stdout=TRUE),"\n",sep="") 24 | sidon 25 | > scalaInfo() 26 | $cmd 27 | [1] "/home/dahl/local/scala/scala/scala-2.12.3/bin/scala" 28 | 29 | $home 30 | [1] "/home/dahl/local/scala/scala/scala-2.12.3" 31 | 32 | $version 33 | [1] "2.12.3" 34 | 35 | $major.release 36 | [1] "2.12" 37 | 38 | > sessionInfo() 39 | R version 3.5.0 (2018-04-23) 40 | Platform: x86_64-pc-linux-gnu (64-bit) 41 | Running under: Ubuntu 16.04.4 LTS 42 | 43 | Matrix products: default 44 | BLAS: /usr/lib/libblas/libblas.so.3.6.0 45 | LAPACK: /usr/lib/lapack/liblapack.so.3.6.0 46 | 47 | locale: 48 | [1] LC_CTYPE=en_US.UTF-8 LC_NUMERIC=C 49 | [3] LC_TIME=en_US.UTF-8 LC_COLLATE=en_US.UTF-8 50 | [5] LC_MONETARY=en_US.UTF-8 LC_MESSAGES=en_US.UTF-8 51 | [7] LC_PAPER=en_US.UTF-8 LC_NAME=C 52 | [9] LC_ADDRESS=C LC_TELEPHONE=C 53 | [11] LC_MEASUREMENT=en_US.UTF-8 LC_IDENTIFICATION=C 54 | 55 | attached base packages: 56 | [1] stats graphics grDevices utils datasets methods base 57 | 58 | other attached packages: 59 | [1] microbenchmark_1.4-4 rscala_2.5.3 60 | 61 | loaded via a namespace (and not attached): 62 | [1] compiler_3.5.0 63 | > 64 | > scala() 65 | > nReps <- 10000 66 | > 67 | > ##### 68 | > 69 | > rng <- s$.scala.util.Random$new() 70 | > rng$nextInt() # First-time compilation 71 | [1] -100414894 72 | > rng$nextInt(1L) # First-time compilation 73 | [1] 0 74 | > nextInt <- rng$nextInt 75 | > nextInt() # Alreary compiled 76 | [1] 908291642 77 | > nextInt(1L) # Alreary compiled 78 | [1] 0 79 | > 80 | > a <- function(rng) s %!% 'rng.nextInt()' 81 | > b <- function(rng) s %.!% 'rng.nextInt()' 82 | > a(rng) 83 | [1] -851951285 84 | > b(rng) 85 | ScalaCachedReference... _: Int 86 | -1187796798 87 | > 88 | > microbenchmark( 89 | + b(rng), 90 | + a(rng), 91 | + rng$nextInt(.AS.REFERENCE=TRUE), 92 | + rng$nextInt(), 93 | + nextInt(), 94 | + rng$nextInt(100L,.AS.REFERENCE=TRUE), 95 | + rng$nextInt(100L), 96 | + nextInt(100L), 97 | + times=nReps 98 | + ) 99 | Unit: microseconds 100 | expr min lq mean median 101 | b(rng) 929.127 1000.3700 1258.1853 1102.528 102 | a(rng) 871.904 954.6465 1186.5723 1053.675 103 | rng$nextInt(.AS.REFERENCE = TRUE) 507.918 561.7185 713.4960 620.971 104 | rng$nextInt() 464.926 513.3415 663.5071 575.125 105 | nextInt() 463.967 504.9320 645.4041 568.609 106 | rng$nextInt(100L, .AS.REFERENCE = TRUE) 678.952 732.3630 926.4079 813.062 107 | rng$nextInt(100L) 627.992 682.8525 879.0694 762.608 108 | nextInt(100L) 620.264 675.5075 853.0284 749.496 109 | uq max neval 110 | 1155.3270 45271.091 10000 111 | 1105.5705 10890.391 10000 112 | 653.9495 7693.163 10000 113 | 604.5935 9413.272 10000 114 | 596.2135 33027.930 10000 115 | 851.7655 42070.277 10000 116 | 799.9475 43874.345 10000 117 | 789.3280 33030.917 10000 118 | > 119 | > 120 | > 121 | > proc.time() 122 | user system elapsed 123 | 61.463 10.495 81.413 124 | -------------------------------------------------------------------------------- /benchmarks/benchmark-references.R: -------------------------------------------------------------------------------- 1 | library(rscala) 2 | library(microbenchmark) 3 | 4 | cat(system2("hostname",stdout=TRUE),"\n",sep="") 5 | scalaConfig() 6 | sessionInfo() 7 | 8 | s <- scala() 9 | nReps <- 10000 10 | 11 | ##### 12 | 13 | rng <- s$.new_scala.util.Random() 14 | rng$nextInt() # First-time compilation 15 | rng$nextInt(1L) # First-time compilation 16 | nextInt <- rng$nextInt 17 | nextInt() # Alreary compiled 18 | nextInt(1L) # Alreary compiled 19 | 20 | microbenchmark( 21 | s(rng=rng) ^ 'rng.nextInt()', 22 | s(rng=rng) * 'rng.nextInt()', 23 | rng$.nextInt(), 24 | rng$nextInt(), 25 | nextInt(), 26 | rng$.nextInt(100L), 27 | rng$nextInt(100L), 28 | nextInt(100L), 29 | times=nReps 30 | ) 31 | -------------------------------------------------------------------------------- /benchmarks/benchmark-references.Rout: -------------------------------------------------------------------------------- 1 | 2 | R Under development (unstable) (2023-01-21 r83656) -- "Unsuffered Consequences" 3 | Copyright (C) 2023 The R Foundation for Statistical Computing 4 | Platform: x86_64-pc-linux-gnu (64-bit) 5 | 6 | R is free software and comes with ABSOLUTELY NO WARRANTY. 7 | You are welcome to redistribute it under certain conditions. 8 | Type 'license()' or 'licence()' for distribution details. 9 | 10 | Natural language support but running in an English locale 11 | 12 | R is a collaborative project with many contributors. 13 | Type 'contributors()' for more information and 14 | 'citation()' on how to cite R or R packages in publications. 15 | 16 | Type 'demo()' for some demos, 'help()' for on-line help, or 17 | 'help.start()' for an HTML browser interface to help. 18 | Type 'q()' to quit R. 19 | 20 | > library(rscala) 21 | > library(microbenchmark) 22 | > 23 | > cat(system2("hostname",stdout=TRUE),"\n",sep="") 24 | abish 25 | > scalaConfig() 26 | 27 | Read configuration file from rscala home: /home/dahl/.rscala/config.R 28 | 29 | $format 30 | [1] 4 31 | 32 | $scalaHome 33 | [1] "/home/dahl/.rscala/scala" 34 | 35 | $scalaCmd 36 | [1] "/home/dahl/.rscala/scala/bin/scala" 37 | 38 | $scalaMajorVersion 39 | [1] "2.13" 40 | 41 | $scalaFullVersion 42 | [1] "2.13.10" 43 | 44 | $javaHome 45 | [1] "/home/dahl/.rscala/java/jre" 46 | 47 | $javaCmd 48 | [1] "/home/dahl/.rscala/java/bin/java" 49 | 50 | $javaMajorVersion 51 | [1] 8 52 | 53 | $javaArchitecture 54 | [1] 64 55 | 56 | $sbtCmd 57 | [1] "/home/dahl/.rscala/sbt/bin/sbt" 58 | 59 | > sessionInfo() 60 | R Under development (unstable) (2023-01-21 r83656) 61 | Platform: x86_64-pc-linux-gnu (64-bit) 62 | Running under: Pop!_OS 22.04 LTS 63 | 64 | Matrix products: default 65 | BLAS/LAPACK: /usr/lib/x86_64-linux-gnu/openblas-pthread/libopenblasp-r0.3.20.so; LAPACK version 3.10.0 66 | 67 | locale: 68 | [1] LC_CTYPE=en_US.UTF-8 LC_NUMERIC=C 69 | [3] LC_TIME=en_US.UTF-8 LC_COLLATE=en_US.UTF-8 70 | [5] LC_MONETARY=en_US.UTF-8 LC_MESSAGES=en_US.UTF-8 71 | [7] LC_PAPER=en_US.UTF-8 LC_NAME=C 72 | [9] LC_ADDRESS=C LC_TELEPHONE=C 73 | [11] LC_MEASUREMENT=en_US.UTF-8 LC_IDENTIFICATION=C 74 | 75 | time zone: America/Denver 76 | tzcode source: system (glibc) 77 | 78 | attached base packages: 79 | [1] stats graphics grDevices utils datasets methods base 80 | 81 | other attached packages: 82 | [1] microbenchmark_1.4.9 rscala_3.2.20 83 | 84 | loaded via a namespace (and not attached): 85 | [1] compiler_4.3.0 tools_4.3.0 86 | > 87 | > s <- scala() 88 | > nReps <- 10000 89 | > 90 | > ##### 91 | > 92 | > rng <- s$.new_scala.util.Random() 93 | > rng$nextInt() # First-time compilation 94 | x1.nextInt 95 | ^ 96 | On line 3: warning: Auto-application to `()` is deprecated. Supply the empty argument list `()` explicitly to invoke method nextInt, 97 | or remove the empty argument list from its definition (Java-defined methods are exempt). 98 | In Scala 3, an unapplied method like this will be eta-expanded into a function. 99 | [1] -745831601 100 | > rng$nextInt(1L) # First-time compilation 101 | [1] 0 102 | > nextInt <- rng$nextInt 103 | > nextInt() # Alreary compiled 104 | [1] -1052981189 105 | > nextInt(1L) # Alreary compiled 106 | [1] 0 107 | > 108 | > microbenchmark( 109 | + s(rng=rng) ^ 'rng.nextInt()', 110 | + s(rng=rng) * 'rng.nextInt()', 111 | + rng$.nextInt(), 112 | + rng$nextInt(), 113 | + nextInt(), 114 | + rng$.nextInt(100L), 115 | + rng$nextInt(100L), 116 | + nextInt(100L), 117 | + times=nReps 118 | + ) 119 | Unit: microseconds 120 | expr min lq mean median uq 121 | s(rng = rng)^"rng.nextInt()" 156.511 182.6590 241.4904 189.0610 211.0890 122 | s(rng = rng) * "rng.nextInt()" 124.660 142.6950 166.0117 146.9390 163.1945 123 | rng$.nextInt() 132.573 147.7510 176.6596 153.0820 169.6555 124 | rng$nextInt() 97.775 111.9985 131.0998 115.4715 126.7290 125 | nextInt() 84.914 103.2745 122.6861 106.7965 117.2325 126 | rng$.nextInt(100L) 143.738 169.6515 201.7519 175.8720 196.4305 127 | rng$nextInt(100L) 110.593 133.8945 155.5879 138.0840 152.1240 128 | nextInt(100L) 108.374 125.0865 145.7246 129.3420 142.0600 129 | max neval 130 | 267236.644 10000 131 | 5468.164 10000 132 | 19060.079 10000 133 | 2870.291 10000 134 | 4643.269 10000 135 | 19477.695 10000 136 | 3634.331 10000 137 | 3037.648 10000 138 | > 139 | > proc.time() 140 | user system elapsed 141 | 10.038 4.474 18.407 142 | -------------------------------------------------------------------------------- /bin/check: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | set -e 4 | 5 | cd $(dirname $(readlink -f "$0"))/.. 6 | 7 | rm -rf rscala.Rcheck 8 | rm -rf R/rscala.Rcheck 9 | bin/package --vignette 10 | 11 | cd R 12 | 13 | R CMD check --as-cran --run-donttest $(ls -1t *.tar.gz | head -1) 14 | 15 | -------------------------------------------------------------------------------- /bin/make-protocol: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env Rscript 2 | 3 | protocolFilename <- "../src/main/scala/org/ddahl/rscala/server/Protocol.scala" 4 | 5 | lines <- scan(protocolFilename,what=character(0),sep="\n",quiet=TRUE) 6 | lines <- lines[grep("^\\s*val\\s+[A-Z_0-9]+\\s*=\\s*.*\\.toByte",lines)] 7 | code <- sub("^\\s*val\\s+","",lines) 8 | code <- sub("\\.toByte\\s*$",")",code) 9 | code <- sub("\\s+$","",code) 10 | code <- sub("= ","<- as.raw(",code) 11 | 12 | con <- file("../R/rscala/R/INTERNAL-protocol.R") 13 | writeLines(code,con) 14 | close(con) 15 | 16 | -------------------------------------------------------------------------------- /bin/package: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env bash 2 | 3 | set -e 4 | 5 | ## For debugging 6 | # set -x 7 | # trap read debug 8 | 9 | PKG_NAME=rscala 10 | 11 | case "$(uname -s)" in 12 | Darwin) 13 | SEP=':' 14 | SEDOPT=.trashme 15 | PKG_HOME=$(dirname "$0")/.. 16 | CWD=$(pwd -P) 17 | cd "$PKG_HOME" 18 | PKG_HOME=$(pwd -P) 19 | cd "$CWD" 20 | ;; 21 | CYGWIN*|MINGW32*|MSYS*) 22 | SEP=';' 23 | SEDOPT="" 24 | PKG_HOME=$(readlink -f $(dirname $(readlink -f "$0"))/..) 25 | ;; 26 | *) 27 | SEP=':' 28 | SEDOPT="" 29 | PKG_HOME=$(readlink -f $(dirname $(readlink -f "$0"))/..) 30 | ;; 31 | esac 32 | 33 | VIGNETTE=FALSE 34 | while [[ $# -gt 0 ]] 35 | do 36 | case "$1" in 37 | "--vignette") 38 | VIGNETTE=TRUE 39 | shift 40 | ;; 41 | *) 42 | shift 43 | ;; 44 | esac 45 | done 46 | 47 | # Make protocal.R script 48 | 49 | cd $PKG_HOME/bin 50 | ./make-protocol 51 | cd .. 52 | 53 | 54 | 55 | # Set version number 56 | 57 | function setversion { 58 | OLDWD="$PWD" 59 | sed -i $SEDOPT 's/\(\s*Version\s*:\s*\)\(.*\)/\1'"$1"'/g' R/$PKG_NAME/DESCRIPTION 60 | sed -i $SEDOPT 's/\(\s*Date\s*:\s*\)\(.*\)/\1'"$2"'/g' R/$PKG_NAME/DESCRIPTION 61 | if [[ "$SEDOPT" ]] 62 | then 63 | rm -f R/$PKG_NAME/DESCRIPTION$SEDOPT 64 | fi 65 | cd "$OLDWD" 66 | } 67 | 68 | PKG_VERSION=$(cat build.sbt | grep "^version := " | cut -d '"' -f 2) 69 | set +e 70 | echo $PKG_VERSION | grep -q SNAPSHOT 71 | if [[ $? == 0 ]] 72 | then 73 | PKG_VERSION=$(echo $PKG_VERSION | sed s/SNAPSHOT/$(date +'%Y%m%d-%H%M')/g) 74 | fi 75 | set -e 76 | setversion $PKG_VERSION $(date +'%Y-%m-%d') 77 | 78 | 79 | # List R resources in the JAR 80 | resourcesDir=src/main/resources/R 81 | rm -rf "$resourcesDir" 82 | mkdir -p "$resourcesDir" 83 | find -L R/rscala/R -name '*.R' -exec cp {} "$resourcesDir" \; 84 | OLDWD="$PWD" 85 | cd $resourcesDir/.. 86 | find -L . -name '*.R' | cut -b 1-1 --complement | sort >| Rscripts 87 | cd "$OLDWD" 88 | 89 | # Compile Scala 90 | 91 | set +e 92 | SBT_FAILED=FALSE 93 | R --slave -e "rscala::scalaSBT()" 94 | if [[ $? != 0 ]] 95 | then 96 | SBT_FAILED=TRUE 97 | echo 98 | echo "***************************************************" 99 | echo "***************************************************" 100 | echo 101 | echo "Please re-run this build script after it completes." 102 | echo 103 | echo "***************************************************" 104 | echo "***************************************************" 105 | echo 106 | fi 107 | set -e 108 | 109 | # Build package 110 | 111 | cd R 112 | cd $PKG_NAME 113 | R --slave -e 'devtools::document(roclets=c("rd", "collate", "namespace"))' 114 | if [[ $? != 0 ]] 115 | then 116 | echo 117 | echo "***************************************************" 118 | echo "***************************************************" 119 | echo 120 | echo "Please re-run this script after executing in R this:" 121 | echo " install.packages(c('devtools','roxygen2','testthat'))" 122 | echo 123 | echo "***************************************************" 124 | echo "***************************************************" 125 | echo 126 | fi 127 | cd .. 128 | if [[ "$SBT_FAILED" == FALSE && "$VIGNETTE" == TRUE ]] 129 | then 130 | R CMD build --compact-vignettes="gs+qpdf" $PKG_NAME 131 | else 132 | R CMD build --no-build-vignettes $PKG_NAME 133 | fi 134 | R CMD INSTALL ${PKG_NAME}_${PKG_VERSION}.tar.gz 135 | cd .. 136 | 137 | -------------------------------------------------------------------------------- /bin/post: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | set -e 4 | 5 | cd $(dirname $(readlink -f "$0"))/.. 6 | 7 | bin/package --vignette 8 | 9 | cd R 10 | TGZ_NAME=$(ls -1t *.tar.gz | head -1) 11 | R CMD check --as-cran $TGZ_NAME 12 | cp -f $TGZ_NAME ../deliveries/$TGZ_NAME 13 | cd .. 14 | 15 | ## Post package 16 | git checkout R/rscala/DESCRIPTION 17 | deploy-R-package deliveries/$TGZ_NAME 18 | 19 | ## Post Scaladoc 20 | R --slave -e "rscala:::scalaSBT(c('packageDoc'),FALSE,FALSE)" 21 | rsync -r --chmod=go=rX target/scala-2.13/api/ dahl.byu.edu:public/rscala/doc 22 | 23 | ## Post vignete 24 | cd deliveries 25 | tar -zxvf $TGZ_NAME rscala/inst/doc/rscala.pdf 26 | rsync --chmod=go=rX rscala/inst/doc/rscala.pdf dahl.byu.edu:public/rscala 27 | rm rscala/inst/doc/rscala.pdf 28 | rmdir rscala/inst/doc 29 | rmdir rscala/inst 30 | rmdir rscala 31 | 32 | -------------------------------------------------------------------------------- /bin/scrape-CRAN-check: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | cd $(dirname $(readlink -f "$0"))/.. 4 | dir=cran-check-results 5 | mkdir -p $dir 6 | cd $dir 7 | 8 | stamp=$(date +'%Y-%m-%d') 9 | wget -O $stamp.rscala.html https://cran.r-project.org/web/checks/check_results_rscala.html 10 | wget -O $stamp.dahl.html https://cran.r-project.org/web/checks/check_results_dahl_at_stat.byu.edu.html 11 | 12 | -------------------------------------------------------------------------------- /bin/setup-remotes: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | # This script sets up pushing to both the official/internal repository and the 4 | # public github mirror. Presummably the repository has already been check out 5 | # using: 6 | # 7 | # git clone git@github.com:dbdahl/rscala.git 8 | # OR 9 | # git clone git@dahl-git.byu.edu:dahl/rscala.git 10 | 11 | cd $(dirname $(readlink -f "$0"))/.. 12 | 13 | if [[ $(git remote -v | wc -l) -gt 2 ]] 14 | then 15 | 2>&1 echo "Note: It seems that the remotes are already set up." 16 | exit 0 17 | fi 18 | 19 | git remote -v | grep "\\(dahl-git.byu.edu\\|github.com\\)" 20 | if [[ $? -ne 0 ]] 21 | then 22 | 2>&1 echo "Error: Remotes not found." 23 | exit 1 24 | fi 25 | 26 | git remote set-url --add --push origin git@github.com:dbdahl/rscala.git 27 | git remote set-url --add --push origin git@dahl-git.byu.edu:dahl/rscala.git 28 | 29 | git remote -v 30 | 31 | -------------------------------------------------------------------------------- /bin/shortcut: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env bash 2 | 3 | set -e 4 | 5 | ## For debugging 6 | # set -x 7 | # trap read debug 8 | 9 | PKG_NAME=rscala 10 | 11 | case "$(uname -s)" in 12 | Darwin) 13 | SEP=':' 14 | SEDOPT=.trashme 15 | PKG_HOME=$(dirname "$0")/.. 16 | CWD=$(pwd -P) 17 | cd "$PKG_HOME" 18 | PKG_HOME=$(pwd -P) 19 | cd "$CWD" 20 | ;; 21 | CYGWIN*|MINGW32*|MSYS*) 22 | SEP=';' 23 | SEDOPT="" 24 | PKG_HOME=$(readlink -f $(dirname $(readlink -f "$0"))/..) 25 | ;; 26 | *) 27 | SEP=':' 28 | SEDOPT="" 29 | PKG_HOME=$(readlink -f $(dirname $(readlink -f "$0"))/..) 30 | ;; 31 | esac 32 | 33 | 34 | cd $PKG_HOME 35 | 36 | 37 | # Set version number 38 | 39 | function setversion { 40 | OLDWD="$PWD" 41 | sed -i $SEDOPT 's/\(\s*Version\s*:\s*\)\(.*\)/\1'"$1"'/g' R/$PKG_NAME/DESCRIPTION 42 | sed -i $SEDOPT 's/\(\s*Date\s*:\s*\)\(.*\)/\1'"$2"'/g' R/$PKG_NAME/DESCRIPTION 43 | if [[ "$SEDOPT" ]] 44 | then 45 | rm -f R/$PKG_NAME/DESCRIPTION$SEDOPT 46 | fi 47 | cd "$OLDWD" 48 | } 49 | 50 | PKG_VERSION=$(cat build.sbt | grep "^version := " | cut -d '"' -f 2) 51 | set +e 52 | echo $PKG_VERSION | grep -q SNAPSHOT 53 | if [[ $? == 0 ]] 54 | then 55 | PKG_VERSION=$(echo $PKG_VERSION | sed s/SNAPSHOT/$(date +'%Y%m%d-%H%M')/g) 56 | fi 57 | set -e 58 | setversion $PKG_VERSION $(date +'%Y-%m-%d') 59 | 60 | 61 | # Build package 62 | 63 | cd R 64 | R CMD build --no-build-vignettes $PKG_NAME 65 | R CMD INSTALL ${PKG_NAME}_${PKG_VERSION}.tar.gz 66 | cd .. 67 | 68 | -------------------------------------------------------------------------------- /bin/tag: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | set -e 4 | cd $(dirname $(readlink -f "$0"))/.. 5 | 6 | MAJOR=$(cat build.sbt | grep "^version := " | cut -d '"' -f 2) 7 | 8 | if [[ $(git status --porcelain | wc -l) -ne 0 ]] 9 | then 10 | 2>&1 echo "The repository is not clean." 11 | exit 1 12 | fi 13 | 14 | git pull 15 | git push 16 | 17 | git tag -a v$MAJOR -m "Version $MAJOR" 18 | git push origin --tags 19 | 20 | -------------------------------------------------------------------------------- /build.sbt: -------------------------------------------------------------------------------- 1 | name := "rscala" 2 | 3 | organization := "org.ddahl" 4 | 5 | version := "3.2.26" 6 | //version := "3.2.26-SNAPSHOT" 7 | 8 | scalaVersion := "2.13.10" 9 | 10 | crossScalaVersions := Seq("2.11.12", "2.12.17", "2.13.10") 11 | 12 | scalacOptions ++= List("-feature", "-deprecation", "-unchecked") 13 | 14 | Compile / doc / sources ~= (_ filter (_.getName endsWith ".scala")) 15 | 16 | Compile / doc / scalacOptions ++= Seq("-no-link-warnings", "-skip-packages", "scala:org.ddahl.rscala.server") 17 | 18 | libraryDependencies ++= List( 19 | "org.scala-lang" % "scala-compiler" % scalaVersion.value 20 | ) 21 | 22 | publishTo := sonatypePublishTo.value 23 | 24 | licenses := List(("Apache-2.0",url("https://www.apache.org/licenses/LICENSE-2.0"))) 25 | 26 | publishMavenStyle := true 27 | 28 | pomExtra := ( 29 | https://github.com/dbdahl/rscala/ 30 | 31 | https://github.com/dbdahl/rscala/ 32 | scm:git:https://github.com/dbdahl/rscala.git 33 | 34 | 35 | 36 | dbdahl 37 | David B. Dahl 38 | https://dahl.byu.edu 39 | 40 | 41 | ) 42 | 43 | -------------------------------------------------------------------------------- /deliveries/rscalaJars_2.3.1.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscalaJars_2.3.1.tar.gz -------------------------------------------------------------------------------- /deliveries/rscalaJars_2.3.2.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscalaJars_2.3.2.tar.gz -------------------------------------------------------------------------------- /deliveries/rscalaJars_2.3.3.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscalaJars_2.3.3.tar.gz -------------------------------------------------------------------------------- /deliveries/rscalaJars_2.3.4.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscalaJars_2.3.4.tar.gz -------------------------------------------------------------------------------- /deliveries/rscalaJars_2.3.5.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscalaJars_2.3.5.tar.gz -------------------------------------------------------------------------------- /deliveries/rscalaJars_2.4.0.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscalaJars_2.4.0.tar.gz -------------------------------------------------------------------------------- /deliveries/rscalaJars_2.5.0.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscalaJars_2.5.0.tar.gz -------------------------------------------------------------------------------- /deliveries/rscalaJars_2.5.1.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscalaJars_2.5.1.tar.gz -------------------------------------------------------------------------------- /deliveries/rscalaJars_2.5.2.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscalaJars_2.5.2.tar.gz -------------------------------------------------------------------------------- /deliveries/rscalaJars_2.5.3.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscalaJars_2.5.3.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_1.0.0.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_1.0.0.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_1.0.1.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_1.0.1.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_1.0.10.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_1.0.10.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_1.0.11.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_1.0.11.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_1.0.12.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_1.0.12.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_1.0.13.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_1.0.13.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_1.0.14.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_1.0.14.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_1.0.2.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_1.0.2.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_1.0.3.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_1.0.3.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_1.0.4.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_1.0.4.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_1.0.5.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_1.0.5.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_1.0.6.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_1.0.6.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_1.0.7.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_1.0.7.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_1.0.8.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_1.0.8.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_1.0.9.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_1.0.9.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_2.0.0.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_2.0.0.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_2.0.1.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_2.0.1.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_2.1.0.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_2.1.0.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_2.1.1.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_2.1.1.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_2.2.0.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_2.2.0.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_2.2.1.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_2.2.1.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_2.2.2.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_2.2.2.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_2.3.1.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_2.3.1.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_2.3.2.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_2.3.2.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_2.3.3.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_2.3.3.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_2.3.4.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_2.3.4.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_2.3.5.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_2.3.5.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_2.4.0.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_2.4.0.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_2.5.0.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_2.5.0.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_2.5.1.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_2.5.1.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_2.5.2.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_2.5.2.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_2.5.3.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_2.5.3.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_3.0.0.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_3.0.0.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_3.0.1.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_3.0.1.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_3.0.2.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_3.0.2.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_3.1.0.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_3.1.0.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_3.2.0.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_3.2.0.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_3.2.1.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_3.2.1.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_3.2.10.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_3.2.10.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_3.2.11.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_3.2.11.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_3.2.12.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_3.2.12.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_3.2.13.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_3.2.13.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_3.2.14.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_3.2.14.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_3.2.15.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_3.2.15.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_3.2.16.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_3.2.16.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_3.2.17.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_3.2.17.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_3.2.18.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_3.2.18.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_3.2.19.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_3.2.19.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_3.2.2.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_3.2.2.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_3.2.21.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_3.2.21.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_3.2.3.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_3.2.3.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_3.2.4.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_3.2.4.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_3.2.5.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_3.2.5.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_3.2.6.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_3.2.6.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_3.2.7.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_3.2.7.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_3.2.8.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_3.2.8.tar.gz -------------------------------------------------------------------------------- /deliveries/rscala_3.2.9.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/deliveries/rscala_3.2.9.tar.gz -------------------------------------------------------------------------------- /examples/callRfromScala-usingPackageJAR: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | export SCALA=$(R --slave -e 'cat(rscala::scalaConfig(verbose=FALSE)$scalaCmd)') 4 | export JAR=$(R --slave -e 'cat(rscala::scalaVersionJARs()[["2.13"]])') 5 | export JAVA_HOME=$(R --slave -e 'cat(rscala::scalaConfig(verbose=FALSE)$javaHome)') 6 | 7 | exec "$SCALA" -nc -cp "$JAR" "$0" "$@" 8 | "$SCALA" -nc -cp "$JAR" 9 | 10 | !# 11 | 12 | val R = org.ddahl.rscala.RClient("R",0,true) 13 | 14 | val a = R.evalD0("sd(rnorm(1000, mean=%-, sd=%-))", 1.0, 2.0) 15 | 16 | R.eval("primes <- %-", Array(2, 3, 5, 7, 11, 13, 17, 19, 23)) 17 | val rFunction = R.evalObject("function(x) x*primes") 18 | val primesTimesTwo = R.evalI1("%-(2)", rFunction) 19 | println(primesTimesTwo.mkString(" ")) 20 | 21 | val m = R.evalI2("matrix(rbinom(%-, size=10, prob=0.5), nrow=2)", 8) 22 | println(m.map(_.mkString(" ")).mkString("\n")) 23 | 24 | R.quit() 25 | 26 | 27 | -------------------------------------------------------------------------------- /examples/callRfromScala/.gitignore: -------------------------------------------------------------------------------- 1 | target 2 | -------------------------------------------------------------------------------- /examples/callRfromScala/CallRFromScala.scala: -------------------------------------------------------------------------------- 1 | import org.ddahl.rscala._ 2 | 3 | object HelloWorldRscala { 4 | 5 | def main(argv: Array[String]): Unit = { 6 | println("Hello World!") 7 | val R = RClient() 8 | println("Goodbye!") 9 | } 10 | 11 | } 12 | 13 | -------------------------------------------------------------------------------- /examples/callRfromScala/build.sbt: -------------------------------------------------------------------------------- 1 | name := "callRfromScala" 2 | 3 | version := "0.0.1" 4 | 5 | libraryDependencies += "org.ddahl" %% "rscala" % "3.2.19" 6 | 7 | -------------------------------------------------------------------------------- /examples/callRfromScala/project/build.properties: -------------------------------------------------------------------------------- 1 | sbt.version=1.2.8 2 | -------------------------------------------------------------------------------- /examples/callRfromScala/run: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | export JAVA_HOME=$(R --slave -e 'cat(rscala::scalaConfig(verbose=FALSE)$javaHome)') 4 | export SBT=$(R --slave -e 'cat(rscala::scalaConfig(verbose=FALSE)$sbt)') 5 | 6 | $SBT run 7 | 8 | -------------------------------------------------------------------------------- /examples/root-finding.R: -------------------------------------------------------------------------------- 1 | library(rscala) 2 | s <- scala() 3 | 4 | bisection <- function(func, lower, upper, epsilon=.Machine$double.eps^0.25) s(g=func, lower=lower, upper=upper, epsilon=epsilon) * ' 5 | val (fLower, fUpper) = (g(lower), g(upper)) 6 | if ( fLower * fUpper > 0 ) sys.error("lower and upper do not straddle the root.") 7 | @scala.annotation.tailrec 8 | def engine(l: Double, u: Double, fLower: Double, fUpper: Double): Double = { 9 | val c = ( l + u ) / 2 10 | if ( math.abs( l - u ) <= epsilon ) c 11 | else { 12 | val fCenter = g(c) 13 | if ( fLower * fCenter < 0 ) engine(l, c, fLower, fCenter) 14 | else engine(c, u, fCenter, fUpper) 15 | } 16 | } 17 | engine(lower, upper, fLower, fUpper) 18 | ' 19 | 20 | 21 | 22 | func1 <- function(a=scalaType("Double"), n=100, target=10) { 23 | sum(a / (1:n + a - 1)) - target 24 | } 25 | 26 | wrapped1 <- { 27 | s(func=scalaPush(func1)) ^ ' 28 | (a: Double) => R.evalD0("%-(%-)", func, a) 29 | ' 30 | } 31 | 32 | wrapped2 <- s ^ func1 33 | 34 | wrapped3 <- s(func=s ^ func1) ^ function(a=scalaType("Double")) { 35 | func(a) 36 | } 37 | 38 | wrapped4 <- s(n=100L, target=10L) ^ '(a: Double) => { 39 | var sum = 0.0 40 | var i = 0 41 | while ( i < n ) { 42 | sum += a / ( i + a ) 43 | i += 1 44 | } 45 | sum - target 46 | } 47 | ' 48 | 49 | 50 | library(microbenchmark) 51 | 52 | microbenchmark( 53 | bisection(wrapped1, 0.1, 20), 54 | bisection(wrapped2, 0.1, 20), 55 | bisection(wrapped3, 0.1, 20), 56 | bisection(wrapped4, 0.1, 20), 57 | uniroot(func1,c(0.1,20)), 58 | times=100) 59 | 60 | 61 | -------------------------------------------------------------------------------- /examples/root-finding.Rout: -------------------------------------------------------------------------------- 1 | 2 | R Under development (unstable) (2019-05-06 r76460) -- "Unsuffered Consequences" 3 | Copyright (C) 2019 The R Foundation for Statistical Computing 4 | Platform: x86_64-pc-linux-gnu (64-bit) 5 | 6 | R is free software and comes with ABSOLUTELY NO WARRANTY. 7 | You are welcome to redistribute it under certain conditions. 8 | Type 'license()' or 'licence()' for distribution details. 9 | 10 | Natural language support but running in an English locale 11 | 12 | R is a collaborative project with many contributors. 13 | Type 'contributors()' for more information and 14 | 'citation()' on how to cite R or R packages in publications. 15 | 16 | Type 'demo()' for some demos, 'help()' for on-line help, or 17 | 'help.start()' for an HTML browser interface to help. 18 | Type 'q()' to quit R. 19 | 20 | > library(rscala) 21 | > s <- scala() 22 | > 23 | > bisection <- function(func, lower, upper, epsilon=.Machine$double.eps^0.25) s(g=func, lower=lower, upper=upper, epsilon=epsilon) * ' 24 | + val (fLower, fUpper) = (g(lower), g(upper)) 25 | + if ( fLower * fUpper > 0 ) sys.error("lower and upper do not straddle the root.") 26 | + @scala.annotation.tailrec 27 | + def engine(l: Double, u: Double, fLower: Double, fUpper: Double): Double = { 28 | + val c = ( l + u ) / 2 29 | + if ( math.abs( l - u ) <= epsilon ) c 30 | + else { 31 | + val fCenter = g(c) 32 | + if ( fLower * fCenter < 0 ) engine(l, c, fLower, fCenter) 33 | + else engine(c, u, fCenter, fUpper) 34 | + } 35 | + } 36 | + engine(lower, upper, fLower, fUpper) 37 | + ' 38 | > 39 | > 40 | > 41 | > func1 <- function(a=scalaType("Double"), n=100, target=10) { 42 | + sum(a / (1:n + a - 1)) - target 43 | + } 44 | > 45 | > wrapped1 <- { 46 | + s(func=scalaPush(func1)) ^ ' 47 | + (a: Double) => R.evalD0("%-(%-)", func, a) 48 | + ' 49 | + } 50 | > 51 | > wrapped2 <- s ^ func1 52 | > 53 | > wrapped3 <- s(func=s ^ func1) ^ function(a=scalaType("Double")) { 54 | + func(a) 55 | + } 56 | > 57 | > wrapped4 <- s(n=100L, target=10L) ^ '(a: Double) => { 58 | + var sum = 0.0 59 | + var i = 0 60 | + while ( i < n ) { 61 | + sum += a / ( i + a ) 62 | + i += 1 63 | + } 64 | + sum - target 65 | + } 66 | + ' 67 | > 68 | > 69 | > library(microbenchmark) 70 | > 71 | > microbenchmark( 72 | + bisection(wrapped1, 0.1, 20), 73 | + bisection(wrapped2, 0.1, 20), 74 | + bisection(wrapped3, 0.1, 20), 75 | + bisection(wrapped4, 0.1, 20), 76 | + uniroot(func1,c(0.1,20)), 77 | + times=100) 78 | Unit: microseconds 79 | expr min lq mean median uq 80 | bisection(wrapped1, 0.1, 20) 5022.151 5186.1325 9840.7388 5384.0330 6768.7540 81 | bisection(wrapped2, 0.1, 20) 402.580 430.0100 612.7956 480.7235 600.1690 82 | bisection(wrapped3, 0.1, 20) 392.396 431.4380 824.9538 467.4040 552.6325 83 | bisection(wrapped4, 0.1, 20) 317.196 341.4285 396.7617 368.9500 413.0580 84 | uniroot(func1, c(0.1, 20)) 39.794 59.5500 115.2601 72.5830 78.5820 85 | max neval 86 | 394418.338 100 87 | 3006.719 100 88 | 30869.990 100 89 | 1086.066 100 90 | 4231.058 100 91 | > 92 | > 93 | > 94 | > proc.time() 95 | user system elapsed 96 | 0.877 0.272 6.155 97 | -------------------------------------------------------------------------------- /others/hanyu-song/parallel-package.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/others/hanyu-song/parallel-package.pdf -------------------------------------------------------------------------------- /others/hanyu-song/psm_ex.RData: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/others/hanyu-song/psm_ex.RData -------------------------------------------------------------------------------- /others/hanyu-song/salso_parallel_ex-DBD.R: -------------------------------------------------------------------------------- 1 | library(parallel) 2 | load('psm_ex.RData') 3 | 4 | cl <- makeCluster(4, type = 'FORK') 5 | clusterEvalQ(cl,library(sdols)) 6 | 7 | ### IMPORTANT: You need to call library(sdols) in clusterEvalQ **BEFORE** doing 8 | ### so in the main script. 9 | 10 | # Check whether this runs 11 | library(sdols) 12 | salso(psm, loss = 'lowerBoundVariationOfInformation') 13 | 14 | res <- parLapply(cl, 1:10, function(i) salso(psm, loss = 'lowerBoundVariationOfInformation', multicore=FALSE)) 15 | 16 | stopCluster(cl) 17 | 18 | -------------------------------------------------------------------------------- /others/hanyu-song/salso_parallel_ex.R: -------------------------------------------------------------------------------- 1 | rscala::scalaHeapMaximum(heap.maximum="2G") 2 | library(sdols) 3 | library(parallel) 4 | load('psm_ex.RData') 5 | # Check whether this runs 6 | salso(psm, loss = 'lowerBoundVariationOfInformation') 7 | 8 | cl <- makeCluster(4, type = 'FORK') 9 | res <- parLapply(cl, 1:1000, salso(psm, loss = 'lowerBoundVariationOfInformation')) 10 | stopCluster(cl) 11 | 12 | mclapply(1:1000, salso(psm, loss = 'lowerBoundVariationOfInformation'), mc.cores = 2) 13 | -------------------------------------------------------------------------------- /project/build.properties: -------------------------------------------------------------------------------- 1 | sbt.version = 1.8.2 2 | -------------------------------------------------------------------------------- /project/plugins.sbt: -------------------------------------------------------------------------------- 1 | scalaVersion := "2.12.17" 2 | addSbtPlugin("org.xerial.sbt" % "sbt-sonatype" % "3.9.15") // "3.8.1") 3 | addSbtPlugin("com.jsuereth" % "sbt-pgp" % "2.1.1") // "2.0.0") 4 | -------------------------------------------------------------------------------- /release-procedure: -------------------------------------------------------------------------------- 1 | Maintenance mode.... 2 | 3 | Run 'install-R --devel' 4 | Bump version number in build.sbt 5 | Update version number in README.md 6 | Update R/rscala/NEWS detailing changes (including the date) 7 | Try to bump to latest versions 8 | project/build.properties 9 | project/plugins.sbt # Skip in maintenance mode 10 | R/rscala/inst/data-raw/urls.txt (with sysdata script) 11 | Run './bin/check' 12 | Move source package from 'R' directory to 'deliveries' directory. 13 | Commit everything to Git, including the package in the deliveries directory. 14 | Run rscala:::verifyDownloads() on Linux, Windows, and Mac OS platforms 15 | Rerun benchmarks on an otherwise idle machine: cd benchmarks; ./all 16 | Test on Linux, Mac OS, and Windows 17 | For Windows, use https://win-builder.r-project.org/ 18 | For Mac, run R CMD check --as-cran --no-build-vignettes --no-manual rscala_VERSION.tar.gz 19 | Try rhub service. 20 | Test depending packages: cd reverse-dependencies; ./check 21 | 22 | ### Skip everything below in maintenance mode.... 23 | 24 | Test examples/callRfromScala-usingPackageJAR 25 | sbt +publishLocal 26 | Update package version number to lastest in examples/callRfromScala/build.sbt 27 | Execute "cd examples/callRfromScala; ./run" 28 | Commit everything to Git, including the package in the deliveries directory. 29 | Tag in Git the version using "bin/tag" script. 30 | sbt +publishSigned 31 | https://oss.sonatype.org/ 32 | -> Log in 33 | -> Staging Repositories 34 | -> orgddahl-???? 35 | -> "Close" repository 36 | -> "Release" repository 37 | # OR 38 | # sbt +sonatypeRelease # Don't worry about the error 'Received 500 error' 39 | Submit to CRAN 40 | Bump (development) version number in build.sbt 41 | -------------------------------------------------------------------------------- /reverse-dependencies/.gitignore: -------------------------------------------------------------------------------- 1 | /output 2 | -------------------------------------------------------------------------------- /reverse-dependencies/check: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | rm -rf output 4 | mkdir output 5 | cp -r packages/*.tar.gz output 6 | 7 | R -e 'tools::check_packages_in_dir("output", reverse = list(), check_args="--as-cran")' 8 | 9 | -------------------------------------------------------------------------------- /reverse-dependencies/list: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env Rscript 2 | 3 | tools::package_dependencies(reverse = TRUE)$rscala 4 | 5 | -------------------------------------------------------------------------------- /reverse-dependencies/packages/bamboo_0.9.23.tar.gz: -------------------------------------------------------------------------------- 1 | ../../../bamboo/deliveries/bamboo_0.9.23.tar.gz -------------------------------------------------------------------------------- /reverse-dependencies/packages/commonsMath_1.2.tar.gz: -------------------------------------------------------------------------------- 1 | ../../../commonsMath/deliveries/commonsMath_1.2.tar.gz -------------------------------------------------------------------------------- /reverse-dependencies/packages/sdols_1.7.tar.gz: -------------------------------------------------------------------------------- 1 | ../../../sdols/deliveries/sdols_1.7.tar.gz -------------------------------------------------------------------------------- /reverse-dependencies/packages/shallot_0.4.5.tar.gz: -------------------------------------------------------------------------------- 1 | ../../../shallot/deliveries/shallot_0.4.5.tar.gz -------------------------------------------------------------------------------- /scratch/.keep: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dbdahl/rscala/600edd4d811a88b4333d7c99ea231d99ee1fc520/scratch/.keep -------------------------------------------------------------------------------- /scratch/scratch.R: -------------------------------------------------------------------------------- 1 | library(rscala) 2 | s <- scala("commonsMath") 3 | s ^ "3+4" 4 | s ^ function(x=stD1) sample(x) 5 | order2 <- s ^ function(x=stS1,decreasing=stL0) order(x,decreasing=decreasing) 6 | x <- c(3,1,5,6,4) 7 | order2(x,TRUE) 8 | order(x,decreasing=TRUE) 9 | 10 | order2(c("a","0","d","b"),TRUE) 11 | 12 | showConnections() 13 | s * "3+4" 14 | showConnections() 15 | scala() 16 | showConnections() 17 | gc() 18 | showConnections() 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | s 27 | s$showCode <- TRUE 28 | 29 | a <- 6 30 | s * '2 + R.evalD0("a")' 31 | 32 | 33 | y <- 2 34 | z <- 3 35 | 36 | a <- function() { 37 | s(x=1,y) * ' 38 | val z = R.evalD0("z") 39 | x + y*z 40 | ' 41 | } 42 | a() 43 | z <- 5 44 | a() 45 | 46 | 47 | b <- s(x=1,y) ^ function() { 48 | z <- evalD0("z") 49 | x + y*z 50 | } 51 | b() 52 | 53 | 54 | bNative <- function(x=1,y1=y) { 55 | x + y1*z 56 | } 57 | bNative() 58 | 59 | 60 | z <- 10 61 | a() 62 | local({ 63 | z <- 29 64 | a() 65 | }) 66 | a() 67 | 68 | b() 69 | local({ 70 | z <- 29 71 | b() 72 | }) 73 | b() 74 | 75 | b() 76 | local({ 77 | print(environment()) 78 | z <- 29 79 | local({ 80 | print(environment()) 81 | z <- 0 82 | local({ 83 | print(environment()) 84 | z <- -10 85 | b() 86 | }) 87 | }) 88 | }) 89 | b() 90 | 91 | bNative() 92 | local({ 93 | z <- 29 94 | bNative() 95 | }) 96 | bNative() 97 | 98 | -------------------------------------------------------------------------------- /scratch/testing: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | exec scala -nc -cp ../R/rscala/inst/java/scala-2.12/rscala_2.12-3.2.0.jar 4 | #scala -nc -cp ../R/rscala/inst/java/scala-2.12/rscala_2.12-3.2.0.jar 5 | 6 | !# 7 | 8 | // val R = org.ddahl.rscala.RClient("R",0,true) 9 | val R = org.ddahl.rscala.RClient() 10 | 11 | val a = R.evalD0("sd(rnorm(1000, mean=%-, sd=%-))", 1.0, 2.0) 12 | R.eval("primes <- %-", Array(2, 3, 5, 7, 11, 13, 17, 19, 23)) 13 | 14 | val rFunction = R.evalObject("function(x) x*primes") 15 | val primesTimesTwo = R.evalI1("%-(2)", rFunction) 16 | 17 | val m = R.evalI2("matrix(rbinom(8, size=10, prob=0.5), nrow=%-)", 4) 18 | 19 | R.quit() 20 | 21 | 22 | 23 | -------------------------------------------------------------------------------- /scratch/todo.txt: -------------------------------------------------------------------------------- 1 | serialize partitions 2 | 3 | what if Java is not installed and I install a package like sdols? 4 | 5 | a <- b <- 2 (Cannot do!) 6 | bell.version1b gives different results than native R! 7 | 8 | -------------------------------------------------------------------------------- /src/main/scala-2.11/org/ddahl/rscala/server/ServerStub.scala: -------------------------------------------------------------------------------- 1 | package org.ddahl.rscala.server 2 | 3 | import scala.tools.nsc.interpreter.IMain 4 | import scala.tools.nsc.interpreter.ILoop 5 | import scala.tools.nsc.Settings 6 | import java.io.PrintWriter 7 | 8 | object ServerStub { 9 | 10 | val Success = scala.tools.nsc.interpreter.IR.Success 11 | 12 | def mkIMain(settings: Settings, printWriter: PrintWriter): IMain = { 13 | val intp = new IMain(settings, printWriter) 14 | val iloop = new ILoop() 15 | iloop.intp = intp 16 | iloop.verbosity() 17 | intp 18 | } 19 | 20 | } 21 | 22 | -------------------------------------------------------------------------------- /src/main/scala-2.11/org/ddahl/rscala/server/TranscompileStub.scala: -------------------------------------------------------------------------------- 1 | package org.ddahl.rscala.server 2 | 3 | trait TranscompileStub { 4 | 5 | } 6 | 7 | -------------------------------------------------------------------------------- /src/main/scala-2.12/org/ddahl/rscala/server/ServerStub.scala: -------------------------------------------------------------------------------- 1 | package org.ddahl.rscala.server 2 | 3 | import scala.tools.nsc.interpreter.IMain 4 | import scala.tools.nsc.interpreter.ILoop 5 | import scala.tools.nsc.Settings 6 | import java.io.PrintWriter 7 | 8 | object ServerStub { 9 | 10 | val Success = scala.tools.nsc.interpreter.IR.Success 11 | 12 | def mkIMain(settings: Settings, printWriter: PrintWriter): IMain = { 13 | val intp = new IMain(settings, printWriter) 14 | val iloop = new ILoop() 15 | iloop.intp = intp 16 | try { 17 | iloop.verbosity() 18 | } catch { 19 | case _: Throwable => 20 | } 21 | intp 22 | } 23 | 24 | } 25 | 26 | -------------------------------------------------------------------------------- /src/main/scala-2.12/org/ddahl/rscala/server/TranscompileStub.scala: -------------------------------------------------------------------------------- 1 | package org.ddahl.rscala.server 2 | 3 | trait TranscompileStub { 4 | 5 | } 6 | 7 | -------------------------------------------------------------------------------- /src/main/scala-2.13/org/ddahl/rscala/server/ServerStub.scala: -------------------------------------------------------------------------------- 1 | package org.ddahl.rscala.server 2 | 3 | import scala.tools.nsc.interpreter.IMain 4 | import scala.tools.nsc.interpreter.shell.{ShellConfig, ReplReporterImpl} 5 | import scala.tools.nsc.{Settings, NewLinePrintWriter} 6 | import java.io.PrintWriter 7 | 8 | object ServerStub { 9 | 10 | val Success = scala.tools.nsc.interpreter.Results.Success 11 | 12 | def mkIMain(settings: Settings, printWriter: PrintWriter): IMain = { 13 | val writer = new NewLinePrintWriter(printWriter, true) 14 | val reporter = new ReplReporterImpl(ShellConfig(settings),settings,writer) 15 | reporter.togglePrintResults() 16 | new IMain(settings, reporter) 17 | } 18 | 19 | } 20 | 21 | -------------------------------------------------------------------------------- /src/main/scala-2.13/org/ddahl/rscala/server/TranscompileStub.scala: -------------------------------------------------------------------------------- 1 | package org.ddahl.rscala.server 2 | 3 | trait TranscompileStub { 4 | 5 | implicit val doubleOrdering = scala.math.Ordering.Double.TotalOrdering 6 | 7 | } 8 | 9 | -------------------------------------------------------------------------------- /src/main/scala/org/ddahl/rscala/server/Conduit.scala: -------------------------------------------------------------------------------- 1 | package org.ddahl.rscala.server 2 | 3 | import Protocol._ 4 | 5 | import scala.collection.mutable.HashMap 6 | 7 | class Conduit(debugger: Debugger) { 8 | 9 | private val maxNArgs: Int = 50 10 | private val argsNames = Array.range(1,maxNArgs+1).map("x"+_) 11 | private val argsLists = Array.range(1,maxNArgs).scanLeft("")((sum,i) => sum + ",x" + i).map(x => if ( x != "" ) x.substring(1) else x).map("(" + _ + ")") 12 | argsLists(0) = "" 13 | 14 | private var stack: List[(Datum,Option[String])] = Nil 15 | 16 | def pop[T](): T = { 17 | val x = stack.head 18 | stack = stack.tail 19 | x._1.value.asInstanceOf[T] 20 | } 21 | 22 | private[rscala] def push(x: Datum, name: Option[String]): Unit = { 23 | stack = (x,name) :: stack 24 | } 25 | 26 | private[rscala] def reset(nArgs: Int): Unit = { 27 | stack = stack.drop(nArgs) 28 | } 29 | 30 | def size: Int = stack.size 31 | 32 | private[rscala] def argsList(nArgs: Int, withReference: Boolean): String = argsLists(nArgs - ( if (withReference) 1 else 0)) 33 | 34 | def mkHeader(nArgs: Int): String = { 35 | val sb = new java.lang.StringBuilder() 36 | stack.take(nArgs).zipWithIndex.foreach { x => 37 | sb.append("val ") 38 | sb.append(x._1._2.getOrElse(argsNames(x._2))) 39 | sb.append(" = conduit.pop[") 40 | val tipe = x._1._1.tipe 41 | val tipeString = tipe match { 42 | case TCODE_REFERENCE => 43 | x._1._1.msg.get 44 | case _ => 45 | Protocol.typeMapper(tipe) 46 | } 47 | sb.append(tipeString) 48 | sb.append("]()\n") 49 | } 50 | sb.toString 51 | } 52 | 53 | var showCode = false 54 | 55 | def debug: Boolean = debugger.on 56 | 57 | def debug_=(value: Boolean) = { 58 | debugger.on = value 59 | } 60 | 61 | } 62 | -------------------------------------------------------------------------------- /src/main/scala/org/ddahl/rscala/server/Datum.scala: -------------------------------------------------------------------------------- 1 | package org.ddahl.rscala.server 2 | 3 | case class Datum(value: Any, tipe: Byte, msg: Option[String]) 4 | 5 | -------------------------------------------------------------------------------- /src/main/scala/org/ddahl/rscala/server/Debugger.scala: -------------------------------------------------------------------------------- 1 | package org.ddahl.rscala.server 2 | 3 | class Debugger(var on: Boolean, out: java.io.PrintWriter, val label: String, val withTime: Boolean) { 4 | 5 | private val maxOutputLength = 2000 6 | 7 | def timestamp(): String = new java.sql.Timestamp(System.currentTimeMillis).toString 8 | 9 | def apply(msg: String): Unit = { 10 | if ( on ) { 11 | val pretext = "DEBUG (" + label + ") " + (if (withTime) timestamp() else "") + ": " 12 | if (msg.length > maxOutputLength) out.println(pretext + msg.substring(0, maxOutputLength - 3) + "...") 13 | else out.println(pretext + msg) 14 | out.flush() 15 | } 16 | } 17 | 18 | } 19 | -------------------------------------------------------------------------------- /src/main/scala/org/ddahl/rscala/server/Main.scala: -------------------------------------------------------------------------------- 1 | package org.ddahl.rscala.server 2 | 3 | import scala.collection.mutable.HashMap 4 | import scala.tools.nsc.interpreter.IMain 5 | import scala.tools.nsc.Settings 6 | import java.io.{BufferedOutputStream, ByteArrayOutputStream, DataInputStream, DataOutputStream, File, PrintWriter} 7 | import java.net.{InetAddress, ServerSocket} 8 | import java.util.concurrent.TimeUnit 9 | import java.nio.file.{FileSystems, Files, NoSuchFileException, Paths, StandardWatchEventKinds} 10 | 11 | object Main extends App { 12 | 13 | val rscalaClasspath = args(0) 14 | val port = args(1).toInt 15 | val portsFilename = args(2) 16 | val sessionFilename = args(3) 17 | val debug = (args(4) == "TRUE") 18 | val serializeOutput = (args(5) == "TRUE") 19 | val buffer = (args(6) == "TRUE") 20 | 21 | // Set up sinks 22 | val (debugger, prntWrtr, baos) = serializeOutput match { 23 | case true => 24 | val out = new ByteArrayOutputStream() 25 | val pw = new PrintWriter(out, false) 26 | val d = new Debugger(debug, pw, "Scala", false) 27 | (d, pw, out) 28 | case false => 29 | val pw = new PrintWriter(System.out, true) 30 | val d = new Debugger(debug, pw, "Scala", false) 31 | (d, pw, null) 32 | } 33 | 34 | // Start session killer 35 | if ( debugger.on ) debugger("starting session killer.") 36 | 37 | object killer extends Thread { 38 | 39 | override def run(): Unit = { 40 | val watchService = FileSystems.getDefault().newWatchService() 41 | val sessionFile = Paths.get(sessionFilename) 42 | if ( ! Files.exists(sessionFile) ) { 43 | if ( debugger.on ) debugger("session file has already been deleted (#1), exiting...") 44 | sys.exit(0) 45 | } 46 | try { 47 | sessionFile.getParent.register(watchService, StandardWatchEventKinds.ENTRY_DELETE) 48 | } catch { 49 | case e: NoSuchFileException => { 50 | if ( debugger.on ) debugger("session file has already been deleted (#2), exiting...") 51 | sys.exit(0) 52 | } 53 | } 54 | while (true) { 55 | // Check for file existence every 10 seconds or whenever R's temp directory changes. 56 | val watchKey = watchService.poll(10, TimeUnit.SECONDS) 57 | if ( watchKey != null ) { 58 | watchKey.pollEvents() 59 | watchKey.reset() 60 | } 61 | if ( ! Files.exists(sessionFile) ) { 62 | if ( debugger.on ) debugger("session file no longer exists, exiting...") 63 | sys.exit(0) 64 | } 65 | } 66 | } 67 | 68 | } 69 | 70 | killer.setDaemon(true) 71 | killer.start() 72 | 73 | // Instantiate interpreter 74 | if ( debugger.on ) debugger("starting interpreter.") 75 | 76 | val settings = new Settings() 77 | settings.embeddedDefaults[Datum] 78 | settings.classpath.value = rscalaClasspath 79 | settings.deprecation.value = true 80 | settings.feature.value = true 81 | settings.unchecked.value = true 82 | settings.language.add("reflectiveCalls") 83 | 84 | val intp = ServerStub.mkIMain(settings, prntWrtr) 85 | 86 | // Set up interpreter 87 | val referenceMap = new HashMap[Int, (Any,String)]() 88 | 89 | if ( debugger.on ) debugger("binding conduit.") 90 | val conduit = new Conduit(debugger) 91 | intp.bind("conduit",conduit) 92 | 93 | if ( debugger.on ) debugger("binding r client.") 94 | val rClient = new org.ddahl.rscala.RClient() 95 | intp.bind("R",rClient) 96 | 97 | val sockets = new Sockets(port, buffer, debugger) 98 | sockets.writePortsFile(portsFilename,prntWrtr) 99 | val (out,in) = sockets.acceptAndSetup() 100 | 101 | // Start main loop 102 | if ( debugger.on ) debugger("entering main loop.") 103 | val server = new Server(intp, sockets, referenceMap, conduit, out, in, debugger, serializeOutput, prntWrtr, baos) 104 | rClient.server = server 105 | server.run() 106 | 107 | } 108 | 109 | -------------------------------------------------------------------------------- /src/main/scala/org/ddahl/rscala/server/Protocol.scala: -------------------------------------------------------------------------------- 1 | package org.ddahl.rscala.server 2 | 3 | object Protocol { 4 | 5 | // Since Scala uses signed bytes and R uses unsigned bytes, stay between 0 and 127 to avoid extra work. 6 | 7 | // commands 8 | 9 | val PCODE_SHUTDOWN = 10.toByte 10 | val PCODE_REXIT = 11.toByte 11 | val PCODE_PUSH_WITH_NAME = 12.toByte 12 | val PCODE_PUSH_WITHOUT_NAME = 13.toByte 13 | val PCODE_CLEAR = 14.toByte 14 | val PCODE_INVOKE = 15.toByte 15 | val PCODE_INVOKE_WITH_REFERENCE = 16.toByte 16 | val PCODE_INVOKE_FREEFORM = 17.toByte 17 | val PCODE_GARBAGE_COLLECT = 18.toByte 18 | val PCODE_SUSPEND = 19.toByte 19 | 20 | // type codes 21 | 22 | val TCODE_INT_0 = 50.toByte 23 | val TCODE_INT_1 = 51.toByte 24 | val TCODE_INT_2 = 52.toByte 25 | val TCODE_DOUBLE_0 = 53.toByte 26 | val TCODE_DOUBLE_1 = 54.toByte 27 | val TCODE_DOUBLE_2 = 55.toByte 28 | val TCODE_LOGICAL_0 = 56.toByte 29 | val TCODE_LOGICAL_1 = 57.toByte 30 | val TCODE_LOGICAL_2 = 58.toByte 31 | val TCODE_RAW_0 = 59.toByte 32 | val TCODE_RAW_1 = 60.toByte 33 | val TCODE_RAW_2 = 61.toByte 34 | val TCODE_CHARACTER_0 = 62.toByte 35 | val TCODE_CHARACTER_1 = 63.toByte 36 | val TCODE_CHARACTER_2 = 64.toByte 37 | val TCODE_UNIT = 65.toByte 38 | val TCODE_REFERENCE = 70.toByte 39 | val TCODE_ROBJECT = 71.toByte 40 | val TCODE_ERROR_DEF = 80.toByte 41 | val TCODE_ERROR_INVOKE = 81.toByte 42 | val TCODE_INTERRUPTED = 82.toByte 43 | val TCODE_CALLBACK = 90.toByte 44 | 45 | // sizes 46 | 47 | val BYTES_PER_INT = 4 48 | val BYTES_PER_DOUBLE = 8 49 | 50 | // type mapper 51 | 52 | val typeMapper = Map( 53 | TCODE_INT_0 -> "Int", 54 | TCODE_INT_1 -> "Array[Int]", 55 | TCODE_INT_2 -> "Array[Array[Int]]", 56 | TCODE_DOUBLE_0 -> "Double", 57 | TCODE_DOUBLE_1 -> "Array[Double]", 58 | TCODE_DOUBLE_2 -> "Array[Array[Double]]", 59 | TCODE_LOGICAL_0 -> "Boolean", 60 | TCODE_LOGICAL_1 -> "Array[Boolean]", 61 | TCODE_LOGICAL_2 -> "Array[Array[Boolean]]", 62 | TCODE_RAW_0 -> "Byte", 63 | TCODE_RAW_1 -> "Array[Byte]", 64 | TCODE_RAW_2 -> "Array[Array[Byte]]", 65 | TCODE_CHARACTER_0 -> "String", 66 | TCODE_CHARACTER_1 -> "Array[String]", 67 | TCODE_CHARACTER_2 -> "Array[Array[String]]", 68 | TCODE_UNIT -> "Unit" 69 | ) 70 | 71 | val typeMapper2 = typeMapper.map(_.swap) 72 | 73 | } 74 | 75 | -------------------------------------------------------------------------------- /src/main/scala/org/ddahl/rscala/server/Sockets.scala: -------------------------------------------------------------------------------- 1 | package org.ddahl.rscala.server 2 | 3 | import java.io.{File, PrintWriter, DataOutputStream, DataInputStream, BufferedOutputStream} 4 | import java.net.{InetAddress, ServerSocket} 5 | 6 | class Sockets(val port: Int, val buffer: Boolean, val debugger: Debugger) { 7 | 8 | // Start server 9 | if ( debugger.on ) debugger("starting server.") 10 | private val ( portS2R, portR2S) = if ( port == 0 ) (0, 0) else (port, port+1) 11 | private val localhost = InetAddress.getByName(null) 12 | private val serverOut = new ServerSocket(portS2R,0, localhost) 13 | private val serverIn = new ServerSocket(portR2S,0, localhost) 14 | 15 | val outPort = serverOut.getLocalPort 16 | val inPort = serverIn.getLocalPort 17 | 18 | def pid: String = { // Starting with Java 9, ProcessHandle.current.pid is the cross-platform and simple solution. 19 | def ensureLong(x: String, fallback: String = "-1"): String = { 20 | try { 21 | x.toLong.toString 22 | } catch { 23 | case _: Throwable => fallback 24 | } 25 | } 26 | val selfFile = new File("/proc/self") 27 | // Note that Scala 2.11 doesn't have util.Properties.isLinux 28 | if ( selfFile.exists && !util.Properties.isWin && !util.Properties.isMac ) ensureLong(selfFile.getCanonicalFile.getName) 29 | else { 30 | val jvmName = java.lang.management.ManagementFactory.getRuntimeMXBean.getName 31 | val tmp = jvmName.indexOf("@") match { 32 | case -1 => "-1" 33 | case i => ensureLong(jvmName.take(i)) 34 | } 35 | if ( tmp == "-1" && util.Properties.isMac ) { 36 | import sys.process._ 37 | ensureLong(Seq("sh", "-c", "echo $PPID").!!.trim) 38 | } 39 | else tmp 40 | } 41 | } 42 | 43 | def writePortsFile(portsFilename: String, printWriter: PrintWriter) = { 44 | try { 45 | val portsFile = new File(portsFilename) 46 | val p = new PrintWriter(portsFile) 47 | p.println("" + outPort + " " + inPort + " " + pid) 48 | p.close() 49 | } catch { 50 | case e: Throwable => // R has already exited? 51 | if (debugger.on) { 52 | printWriter.println(e) 53 | e.printStackTrace(printWriter) 54 | debugger("cannot write to ports file, exiting...") 55 | } 56 | sys.exit(0) 57 | } 58 | } 59 | 60 | def acceptAndSetup(): (DataOutputStream, DataInputStream) = { 61 | if (debugger.on) debugger("socket S2R waiting for client on port " + serverOut.getLocalPort + ".") 62 | val sOut = serverOut.accept() 63 | if (debugger.on) debugger("socket R2S waiting for client on port " + serverIn.getLocalPort + ".") 64 | val sIn = serverIn.accept() 65 | val bos = if ( buffer ) new BufferedOutputStream(sOut.getOutputStream) else sOut.getOutputStream 66 | val out = new DataOutputStream(bos) 67 | val in = new DataInputStream(sIn.getInputStream) 68 | if ( debugger.on ) debugger("connections established.") 69 | (out,in) 70 | } 71 | 72 | } 73 | 74 | --------------------------------------------------------------------------------