正如主题所描述的,我正在寻找一种方法来实现这一目标:
require("R6")
R6cls <- R6::R6Class("R6obj",
public = list(val = 1, foo = function() "foo!")
)
# check this R6 class
r6o <- R6cls$new()
r6o
# <R6obj>
# Public:
# clone: function (deep = FALSE)
# foo: function ()
# val: 1
# now the S4 part
S4wR6slot <- function() new("S4wR6slot")
setClass("S4wR6slot", contains = "environment", # or maybe "R6" or "R6cls"? tried them all but none seemed to work
slots = list(a = "R6cls", b = "character"))
# Currently gives
Warning message:
undefined slot classes in definition of "S4wR6slot": a(class "R6cls")
# but you can still kind of use it
s4r6 <- S4wR6slot()
s4r6
# An object of class "S4wR6slot"
# <environment: 0x00000179de2da628>
# Slot "a":
# NULL
#
# Slot "b":
# character(0)
s4r6@b <- "text" # works nicely
# BUT trying to assign to that env slot
s4r6@a <- r6o
# will throw these "ugly" errors
Error in (function (cl, name, valueClass) :
c("assignment of an object of class “R6obj” is not valid for @‘a’ in an object of class “S4wR6slot”; is(value, \"R6cls\") is not TRUE",
"assignment of an object of class “R6” is not valid for @‘a’ in an object of class “S4wR6slot”; is(value, \"R6cls\") is not TRUE")
使用setOldClass()
也没有什么好处。
也许根本没有办法做到这一点——只是询问某人是否有想法?或者甚至可能实现了这一点 - 否则也许我的 rtfm 做得不够好,有人可以向我指出文档,其中说你不应该尝试使这项工作起作用?
最佳答案
有一种方法可以在 S4 类中包含 R6 对象,但涉及通过定义名为“R6”的 S4
类来欺骗 S4 系统。这将防止 methods
包提示类 R6 不存在。幸运的是,它实际上并没有检查原型(prototype)中的“R6”对象是否是 S4 类型,因此您可以将实际的 R6 对象粘贴在那里。
library(R6)
R6cls <- R6::R6Class("R6obj",
public = list(val = 1, foo = function() "foo!")
)
setClass('R6')
setClass("S4wR6slot", slots = list(a = 'R6', b = "character"),
prototype = list(a = R6cls$new(), b = 'Hello'))
S4wR6slot <- function() new("S4wR6slot")
myS4 <- S4wR6slot()
class(myS4)
#> [1] "S4wR6slot"
#> attr(,"package")
#> [1] ".GlobalEnv"
isS4(myS4)
#> [1] TRUE
myS4@a
#> <R6obj>
#> Public:
#> clone: function (deep = FALSE)
#> foo: function ()
#> val: 1
关于r - 有没有办法将 R6 对象分配给 S4 对象槽?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/72559243/