Lớp S4 của tôi có một phương thức được gọi nhiều lần. Tôi nhận thấy rằng thời gian thực hiện chậm hơn nhiều so với khi một chức năng tương tự được gọi là độc lập. Vì vậy, tôi đã thêm một vị trí có loại "hàm" vào lớp của tôi và sử dụng hàm đó thay vì phương thức. Ví dụ dưới đây cho thấy hai cách làm điều này, và cả hai cách này chạy nhanh hơn nhiều so với phương thức tương ứng. Ngoài ra, ví dụ cho thấy rằng tốc độ thấp hơn của phương pháp không phải là do phương pháp phải lấy dữ liệu từ lớp, vì các hàm nhanh hơn ngay cả khi chúng cũng làm điều đó.Phương pháp S4 có được gửi chậm không?
Tất nhiên, cách làm việc này không lý tưởng. Tôi tự hỏi nếu có một cách để tăng tốc công văn phương pháp. Bất kỳ đề xuất?
setClass(Class = "SpeedTest",
representation = representation(
x = "numeric",
foo1 = "function",
foo2 = "function"
)
)
speedTest <- function(n) {
new("SpeedTest",
x = rnorm(n),
foo1 = function(z) sqrt(abs(z)),
foo2 = function() {}
)
}
setGeneric(
name = "method.foo",
def = function(object) {standardGeneric("method.foo")}
)
setMethod(
f = "method.foo",
signature = "SpeedTest",
definition = function(object) {
sqrt(abs([email protected]))
}
)
setGeneric(
name = "create.foo2",
def = function(object) {standardGeneric("create.foo2")}
)
setMethod(
f = "create.foo2",
signature = "SpeedTest",
definition = function(object) {
z <- [email protected]
[email protected] <- function() sqrt(abs(z))
object
}
)
> st <- speedTest(1000)
> st <- create.foo2(st)
>
> iters <- 100000
>
> system.time(for (i in seq(iters)) method.foo(st)) # slowest by far
user system elapsed
3.26 0.00 3.27
> # much faster
> system.time({foo1 <- [email protected]; x <- [email protected]; for (i in seq(iters)) foo1(x)})
user system elapsed
1.47 0.00 1.46
> # retrieving [email protected] instead of x does not affect speed
> system.time({foo1 <- [email protected]; for (i in seq(iters)) foo1([email protected])})
user system elapsed
1.47 0.00 1.49
> # same speed as foo1 although no explicit argument
> system.time({foo2 <- [email protected]; for (i in seq(iters)) foo2()})
user system elapsed
1.44 0.00 1.45
# Cannot increase speed by using a lambda to "eliminate" the argument of method.foo
> system.time({foo <- function() method.foo(st); for (i in seq(iters)) foo()})
user system elapsed
3.28 0.00 3.29
Cảm ơn đề xuất hữu ích. Lý do dữ liệu của tôi đại diện và phương pháp không vectorized: Tôi đang sử dụng đa hình. Trong mã của tôi, tôi có một method.foo khác nhau cho mỗi lớp con và những người khác nhau có thể viết các phương thức khác nhau. Vì vậy, khác với ví dụ, mỗi lời gọi hàm method.foo gọi một phương thức khác và tôi không biết cái gì nằm trong phần thân của mỗi phương thức. – Soldalma