Share
Embed
R7: A first look
Hadley Wickham
June 21, 2022
Transcript
18 slides
-
Hadley Wickham on behalf of The R Consortium Working
Group on OOP https://rconsortium.github.io/OOP-WG/ R7: A fi rst look at a new OOP system for R June 2022 -
bizarro < - function(x) { if (is.numeric(x)) { - x
} else if (is.logical(x)) { !x } else if (is.character(x)) { str_reverse(x) } else if (is.factor(x)) { levels(x) < - rev(level(x)) x } else { stop("Not supported") } } Why do we need OOP? This is even more important for functions in base R, like print() -
S3 S4 English Fairy Tales (1918) by Flora Annie Steel,
illustrated by Arthur Rackham R7 R7 = S3 + S4 -
library(R7) bizarro < - new_generic("bizarro", "x") With R7, we fi
rst de fi ne a generic Name of the generic Name of the argument used for dispatch -
method(bizarro, class_numeric) < - function(x) { - x } method(bizarro,
class_logical) < - function(x) { !x } method(bizarro, class_character) < - function(x) { str_reverse(x) } Then we de fi ne methods Name of the generic Built-in class -
bizarro #> <R7_generic> function (x, . . . ) with
4 methods: #> 1 : method(bizarro, "integer") #> 2 : method(bizarro, "double") #> 3 : method(bizarro, "character") #> 4 : method(bizarro, "logical") -
bizarro(1) #> [1] -1 bizarro(TRUE) #> [1] FALSE bizarro(mean) #>
Error: generic `bizarro()` can't f i nd method #> for function object -
range < - new_class("range", properties = list( start = class_numeric,
end = class_numeric ) ) Creating a new class Name of the class Property type Property name Constructor function -
x < - range(start = 1, end = 10) x
#> <range> #> @ start: num 1 #> @ end : num 10 x@start x@end < - 20 x@end < - "x" #> Error: <range>@end must be <double>, not <character> -
r < - range(start = 10, end = 1)
#> <range> #> @ start: num 10 #> @ end : num 1 But… -
range < - new_class("range", properties = . . . ,
validator = function(self) { if (length(self@start) ! = 1) { "@start must be length 1" } else if (length(self@end) ! = 1) { "@end must be length 1" } else if (self@end < self@start) { "@end must be greater than or equal to @start" } } ) Can add a validator to prevent that from happening -
range < - new_class("range", properties = list( start = class_double,
end = class_double, length = new_property( getter = function(self) self@end - self@start, ) ), … ) Can also create dynamic properties -
S3 S4 English Fairy Tales (1918) by Flora Annie Steel,
illustrated by Arthur Rackham R7 -
1. Team e ff ort. 2. Formal de fi nition
of class and properties (like S4). 3. Embrace data access. 4. Backward compatible with S3. 5. Pit of success. Why do we hope this will succeed? -
Please try it out! https://rconsortium.github.io/OOP-WG/ remotes : : install_github("rconsortium/OOP-WG") What
doesn’t work? What don’t you understand? These slides at https://speakerdeck.com/hadley/r7-a- fi rst-look