Mã của tôi chạy chậm!

Viết mã R hiệu quả

Colin Gillespie

Jumping Rivers & Newcastle University

Mã của tôi có thật sự chậm?

  • 1 giây?
  • 1 phút?
  • 1 giờ?
Viết mã R hiệu quả

Mã của tôi có thật sự chậm?

Viết mã R hiệu quả

Benchmarking

  1. Gói một hàm quanh tính năng cần đo hiệu năng
  2. Bấm giờ hàm trong các kịch bản khác nhau, ví dụ, kích thước dữ liệu
Viết mã R hiệu quả

Ví dụ: Dãy số

$$ 1, 2, 3, \ldots, n $$

Phương án 1
1:n
Phương án 2
seq(1, n)
Phương án 3
seq(1, n, by = 1)
Viết mã R hiệu quả

Đóng gói hàm

colon <- function(n) 1:n
colon(5)
1 2 3 4 5
seq_default <- function(n) seq(1, n)
seq_by <- function(n) seq(1, n, by = 1)
Viết mã R hiệu quả

Đo thời gian với system.time()

system.time(colon(1e8))
#   user  system elapsed
#  0.032   0.028   0.060
system.time(seq_default(1e8))
#   user  system elapsed
#  0.060   0.028   0.086
system.time(seq_by(1e8))
#   user  system elapsed
#  1.088   0.520   1.600
  • Thời gian user là thời gian CPU tính cho lệnh của người dùng.
    • Thời gian system là thời gian CPU hệ thống dùng thay cho tiến trình gọi.
    • Thời gian elapsed xấp xỉ tổng user và system; đây là con số ta thường quan tâm.
Viết mã R hiệu quả

Lưu kết quả

Vấn đề với

system.time(colon(1e8))

là ta chưa lưu kết quả. Cần chạy lại để lưu kết quả

res <- colon(1e8)

Toán tử <- thực hiện cả hai:

  • Truyền đối số
  • Gán đối tượng
system.time(res <- colon(1e8))

Toán tử = chỉ thực hiện một trong hai:

  • Truyền đối số
  • Gán đối tượng
# Gây lỗi
system.time(res = colon(1e8))
Viết mã R hiệu quả

Thời gian tương đối

Method Thời gian tuyệt đối (giây) Thời gian tương đối
colon(n) 0.060 $0.060/0.060 = 1.00$
seq_default(n) 0.086 $0.086/0.060 = 1.40$
seq_by(n) 1.607 $1.60/0.060 = 26.7$
Viết mã R hiệu quả

Gói microbenchmark

  • So sánh các hàm
    • Mỗi hàm chạy nhiều lần
library("microbenchmark")

n <- 1e8 microbenchmark(colon(n), seq_default(n), seq_by(n), times = 10) # Chạy mỗi hàm 10 lần
# Unit: milliseconds
#           expr  min   lq  mean  median   uq  max neval cld
#       colon(n)   59  130   220     202  341  391    10  a
# seq_default(n)   94  204   290     337  348  383    10  a
#      seq_by(n) 1945 2044  2260    2275 2359 2787    10   b
Viết mã R hiệu quả

Cùng luyện tập nào!

Viết mã R hiệu quả

Preparing Video For Download...