Given an R6 class Class1
with its initialize
function, I would like to be able to pass an instance of the same class and return it directly.
Something like this:
if("Class1" %in% class(x)) x
else Class1$new(x)
But inside the initialize
function of an R6 class, that should work like this
# This script does not work
# Definition of the class
Class1 = R6::R6Class("Class1",
public=list(
initialize = function(x){
# This line does not work
if("Class1"%in%class(x)) return(x)
}
))
# Initiate an instance from scratch
foo = Class1$new()
# Initiate an instance through another instance
bar = Class1$new(foo)
# The two should be the same
identical(foo, bar)
#> TRUE
Under current state of R6 this seems to not be possible. Check the raw code github.com/r-lib/R6/blob/master/R/new.R . Most important are lines 154 where is initialization applied and 194 where public_bind_env is returned . The problem is that even with super assignment I think we could not overwrite it as all things are built here from a new empty env with own address. This solution which using a wrapper is widthly used in the market and it is doing what it should:
class1 <- function(x = NULL) {
if(inherits(x, "Class1")) x else Class1$new(x)
}
Class1 = R6::R6Class("Class1",
public=list(
initialize = function(x = NULL){
}
))
# Initiate an instance from scratch
foo = class1()
# Initiate an instance through another instance
bar = class1(foo)
# The two should be the same
identical(foo, bar)
#> TRUE