r-lib / R6

Encapsulated object-oriented programming for R
https://R6.r-lib.org
Other
404 stars 56 forks source link

Override clone behavior #178

Closed dfalbel closed 5 years ago

dfalbel commented 5 years ago

I opened an SO post here.

The idea is that sometimes I have a class that keeps a pointer to a C++ object, for example:

myClass <- R6::R6Class(
  "myClass", 
  public = list(
    xp = NULL,
    initialize = function(x) {
      self$xp = cpp_fun_that_returns_a_pointer(x)
    }
  )
)

When cloning this class (even with deep=TRUE) the c++ object won't be cloned. So it would be nice to be able to override the clone method behavior. Is it possible?

Maybe allow it only when cloneable = FALSE.

dfalbel commented 5 years ago

This is somewhat related to #176 where one could benefit of being able to create a custom clone method.

dfalbel commented 5 years ago

This seems to be already possible. Quoting here the answer from @duckmayr on SO.

# Set up the R6 class, making sure to set cloneable to FALSE
myClass <- R6::R6Class(
    "myClass", 
    public = list(
        xp = NULL,
        initialize = function(x = 1:3) {
            self$xp = x
        }
    ),
    cloneable = FALSE
)
# Set the clone method
myClass$set("public", "clone", function() {
    print("This is a custom clone method!") # Test print statement
    myClass$new(self$xp)
})
# Make a new myClass object
a <- myClass$new(x = 4:6)
# Examine it
a
#> <myClass>
#>   Public:
#>     clone: function () 
#>     initialize: function (x = 1:3) 
#>     xp: 4 5 6
# Clone it
b <- a$clone()
#> [1] "This is a custom clone method!"
# We see the test print statement was printed!
# Let's check out b:
b
#> <myClass>
#>   Public:
#>     clone: function () 
#>     initialize: function (x = 1:3) 
#>     xp: 4 5 6