rpackagevariable-assignmentassign

How to write/override your own assignment function as in `names<-`?


Inspired by the way the names<- function works I want to be able to do something similar inside a package.


Reproducible example

Create an empty package and add the following file:

## R/internal-state.R
the <- new.env(parent = emptyenv())

#' @export
object <- function(name) the[[name]]

#' @export
set_object <- function(name, value) the[[name]] <- value

Then on the console:

> usethis::use_namespace() ## and choose Yes
> devtools::document()

After that, install package with CTRL+SHIFT+B


Now you can do this:

> library(testpackage)
> set_object("foo", 1)
> object("foo")
[1] 1

Question

How to modify this example to be able to do that?

> library(testpackage)
> object("foo") <- 1
> object("foo")
[1] 1

Solution

  • You can't use a function like this if the first value is not "assignable". Here you have the literal string value "foo" and you cannot assign a value to that literal value so the fancy function<- syntactic sugar will not work. When you use names(x) <- "a" the x value is a variable that can be updated. The call is translated to something like

    x <- `names<-`(x, "a")
    

    This means object("foo") <- 1 would become

    "foo" <- `object<-`("foo", 1)
    

    which doesn't make sense