我想写一个S4对象,以便它可以传递给只接受S3对象的方法.(似乎setOldClass()可能与此有关,但我从文档中不清楚这一点?)
例如,对于一个最小的例子,想象一下我有S3类和函数:
myS3 <- list(a = 1, b = 2)
class(myS3) <- "myS3class"
myS3function.myS3class <- function(x) x$a + x$b
Run Code Online (Sandbox Code Playgroud)
我有S4对象
setClass("myS4class", representation(a = "numeric", b = "numeric"))
obj <- new("myS4class", a = 1, b = 2)
Run Code Online (Sandbox Code Playgroud)
有什么我可以这样做的吗?
myS3function.myS3class(obj)
Run Code Online (Sandbox Code Playgroud)
给了我同样的东西
myS3function.myS3class(myS3)
Run Code Online (Sandbox Code Playgroud)
通过仅修改S4类?
编辑我这种方法的基本原理是利用S3类的所有现有方法(通常可能来自其他包等),而不必重写它们.我意识到一种方法只是编写一个强制方法(setAs()),将我的S4对象转换为S3对象,但用户总是必须手动执行此步骤.(虽然它有效,但我也有点不清楚使用setAs()S4类到S3类是否是不好的做法,而不是在S4类之间进行映射).
从我阅读文档的方式来看setOldClass,听起来这可以使S3对象像S4对象一样?那是对的吗?如果是这样,我的问题是,是否可以反过来(可能是通过prototype在S4类中设置?).
如果这是不可能的,那么解释为什么这会是一个坏主意的理由呢?
向 S4 类添加一个方法,将其转换为 S3 类。
setGeneric(
"as.myS3class",
function(object)
{
standardGeneric("as.myS3class")
}
)
setMethod(
"as.myS3class",
signature(object = "myS4class"),
function(object)
{
structure(list(a = object@a, b = object@b), class = "myS3class")
}
)
Run Code Online (Sandbox Code Playgroud)
然后你可以像这样调用S3方法:
myS3function(as.myS3class(obj))
Run Code Online (Sandbox Code Playgroud)