Estou tentando usar o novo S7 OOP que está sendo apresentado ao R ( https://github.com/RConsortium/S7 ). Eu gostaria de usar o S7 para agrupar um método S3 para o operador unário |
.
Tenho um objeto class "ggsurvfit"
e gostaria de definir três novos métodos:
`|`(ggsurvfit, ggsurvfit)
`|`(ggsurvfit, ggplot)
`|`(ggplot, ggsurvfit)
Algumas semanas atrás, tive a sorte de estar na mesma sala com Hadley Wickham (que faz parte da equipe R Consortium que desenvolve o S7) e ele gentilmente me forneceu o código abaixo para encapsular o método S3 usando S7. (Eu adicionei a string de texto retornada para sua informação)
method(`|`, list(new_S3_class("ggsurvfit"), new_S3_class("ggsurvfit"))) <- function(e1, e2) {
"This is ggsurvfit|ggsurvfit"
}
method(`|`, list(new_S3_class("ggsurvfit"), new_S3_class("ggplot"))) <- function(e1, e2) {
"This is ggsurvfit|ggplot"
}
method(`|`, list(new_S3_class("ggplot"), new_S3_class("ggsurvfit"))) <- function(e1, e2) {
"This is ggplot|ggsurvfit"
}
O problema que estou tendo é que não consigo iniciar/acionar esses métodos. No exemplo abaixo, eu esperava/esperava que a operação retornasse a string "This is ggsurvfit|ggplot"
. O que estou perdendo aqui? OBRIGADO!
library(ggsurvfit)
#> Loading required package: ggplot2
S7::method(`|`, list(S7::new_S3_class("ggsurvfit"), S7::new_S3_class("ggplot"))) <- function(e1, e2) {
"This is ggsurvfit|ggplot"
}
plot1 <-
survfit2(Surv(time, status) ~ sex, data = df_lung) |>
ggsurvfit() +
add_risktable()
class(plot1)
#> [1] "ggsurvfit" "gg" "ggplot"
plot2 <-
ggplot(mtcars, aes(mpg, cyl)) +
geom_point()
class(plot2)
#> [1] "gg" "ggplot"
ret <- plot1 | plot2
#> Error in plot1 | plot2: operations are possible only for numeric, logical or complex types
Criado em 10/10/2023 com reprex v2.0.2
Acho que o problema é que
|
não é um método S7 e"ggsurvfit"
não é uma classe S7. Os documentos dizem sobremethod<-
issoAgrupar uma classe S3 existente
new_S3_class
não a torna uma classe S7 - apenas declara que a classe que você deseja usar é S3. Como você provavelmente não deseja criar|
um S7 genérico, sua melhor opção pode ser agrupar seu ggsurvfit em uma classe S7. Isso parece funcionar:Claro, você precisará criar o
ggsurvfit
wrapper para este exemplo. Na produção, você provavelmente reescreveria ggsurvfit para ser uma classe S7, mas isso lhe dá a ideia:Mas o comportamento correto é observado:
Claro, você precisará definir um
print
método para o seu wrapper, mas isso parece muito simples no S7Criado em 10/10/2023 com reprex v2.0.2