Computer >> Máy Tính >  >> Lập trình >> Ruby

Đừng cố ý:Phương tiện thống kê và tỷ lệ phần trăm 101

Giám sát hiệu suất là một phần quan trọng để chạy một ứng dụng thành công. Một trong những cách cơ bản nhất để cho biết hiệu suất của cái gì đó là đo khoảng thời gian mỗi khi nó xảy ra và chắt lọc số liệu thống kê từ nó.

Trung bình

Giá trị trung bình hoặc giá trị trung bình của một tập hợp các giá trị là một khởi đầu tốt để xem điều gì đó tốt hay xấu hoạt động như thế nào. Nó được tính bằng cách tổng tất cả các giá trị đang được xem xét và sau đó chia cho số lần xuất hiện.

Trong Ruby, đây là cách tính thời gian phản hồi trung bình sẽ trông như thế nào:

def mean(array)
 (array.sum.to_f / array.length).round(2)
end
 
durations = [1,2,3,4,5,6,7,8,9,0]
mean(durations) #=> 4.5

Lưu ý :Trong ví dụ, để có kết quả chính xác hơn khi chia, chúng tôi chuyển tổng giá trị thời lượng thành Float. Nếu không, Ruby sẽ làm tròn xuống Số nguyên gần nhất, trả về 4 thay vào đó.

Trung vị

Một thống kê hữu ích khác là giá trị trung vị. Mặc dù nghe có vẻ giống nhau, nhưng có sự khác biệt giữa giá trị trung bình và giá trị trung bình của một tập hợp các giá trị.

Giá trị trung bình là giá trị phân tách nửa trên của tập hợp với nửa dưới của tập hợp.

Đối với tập dữ liệu có số giá trị lẻ, bạn lấy giá trị trung vị bằng cách sắp xếp các giá trị trước tiên, sau đó chọn số ở giữa. Đối với một tập hợp có số giá trị chẵn, sau khi sắp xếp chúng, giá trị trung bình sẽ là giá trị trung bình của hai số ở giữa.

def median(array)
  sorted_array = array.sort
  length = sorted_array.length
 
  if length.odd? # Middle number for odd arrays
    sorted_array[length / 2]
  else # Mean of two middle numbers
    first_value = sorted_array[length / 2]
    second_value = sorted_array[length / 2 - 1]
    (first_value + second_value) / 2.to_f
  end
end
 
# Even array
durations = [1,2,3,4,5,6,7,8,9,0]
median(durations) #=> 4.5
 
# Odd array
durations = [1,1,2,3,4,5,6,7,8,9,0]
median(durations) #=> 4

Thống kê này là một cách tốt để xem liệu có sự sai lệch lớn trong dữ liệu hay một cái đuôi dài.

durations = [1,2,3,4,5,2000]
 
median(durations) #=> 3.5
mean(durations) #=> 335.83

Giá trị trung bình cho các khoảng thời gian ở trên sẽ là 335.83 bởi vì một ngoại lệ duy nhất là 2000ms. Giá trị trung bình, chỉ là 3.5 , chỉ ra rằng có một sai lệch.

Bằng cách tính cả giá trị trung bình và giá trị trung bình của một tập dữ liệu, bạn có thể tìm ra liệu có bất kỳ giá trị ngoại lệ lớn nào hoặc phần đuôi dài hay không.

Vấn đề với Trung bình

Mặc dù giá trị trung bình và giá trị trung bình là những chỉ số tốt về hiệu suất, nhưng chúng không nói lên toàn bộ câu chuyện. Nếu bạn yêu cầu một trang web mười lần, mức trung bình có thể rất thấp, nhưng một hoặc nhiều yêu cầu vẫn có thể mất rất nhiều thời gian để hoàn thành.

Hình ảnh bên dưới cho thấy phần trăm thứ 99 (xanh lam) và 90 (xanh lá cây) và giá trị trung bình (đỏ) cho một hành động nhất định trong AppSignal. Bạn có thể thấy rằng số 99 và 90 là khá xa so với mức trung bình và có một số đột biến. Điều này có nghĩa là mặc dù khách hàng bình thường của bạn có trải nghiệm tốt, nhưng thỉnh thoảng lại có một người dùng phải đợi trang hiển thị lâu hơn gần gấp đôi. Lý tưởng nhất là bạn muốn nhận được tất cả các giá trị này càng gần nhau càng tốt, tạo ra trải nghiệm nhất quán hơn cho tất cả người dùng của bạn.

Ví dụ:với thời lượng sau được đặt trong đó 10 khách hàng yêu cầu một trang có thời lượng từ 100 mili giây đến 1 giây.

[100,100,100,100,100,100,100,100,100,1_000]

Điều này sẽ dẫn đến giá trị trung bình chỉ là 190ms trong khi một người dùng có trải nghiệm rất tệ về thời gian phản hồi 1 giây. Khi chỉ theo dõi giá trị trung bình, bạn sẽ dễ dàng nghĩ rằng trang web của mình có hiệu suất tuyệt vời, trong khi thực tế, thỉnh thoảng người dùng lại có một trải nghiệm tồi tệ.

Ví dụ trên chỉ dành cho 10 yêu cầu, nhưng hãy tưởng tượng nếu bạn có một nghìn yêu cầu mỗi ngày, điều đó có nghĩa là một trăm người dùng trong số đó đã có một trải nghiệm tồi tệ.

Phần trăm

Để cung cấp ý tưởng tốt hơn về sự phân bố của các giá trị, chúng tôi sử dụng các phân vị. Phần trăm tương tự như số trung vị - một con số biểu thị một điểm trong tập dữ liệu trong đó một nửa tập hợp nằm dưới số và một nửa tập hợp ở trên. Phần trăm tương tự theo nghĩa là phần trăm thứ 20 có nghĩa là 20% số trong tập dữ liệu thấp hơn con số đó.

Cho tập hợp (đã sắp xếp) sau:

[100,100,200,200,300,300,400,400,500,5_000]

Nếu chúng ta muốn biết phân vị thứ 20, chúng ta có thể tính nó theo cách sau:Có 10 giá trị trong tập hợp. Giá trị mong muốn ở vị trí 1 (20.0 / 100 * 10 - 1 ) khi mảng của chúng ta bắt đầu từ 0. Vì mảng này chứa một lượng mục chẵn, chúng tôi phải tính giá trị trung bình giữa chỉ số (2 ) và chỉ mục + 1 (3 ). Điều này sẽ dẫn đến giá trị 150 cho phân vị thứ 20.

Một triển khai Ruby rất ngây thơ sẽ trông như thế này:

def percentile(array, wanted_percentile)
  sorted_array = array.sort
 
  index = (wanted_percentile.to_f / 100) * sorted_array.length - 1
 
  # Check if index is not a round number
  if index != index.to_i
    sorted_array.at(index.ceil)
  elsif sorted_array.length.even?
    first_value = sorted_array.at(index)
    second_value = sorted_array.at(index + 1)
    (first_value + second_value) / 2
  else
    sorted_array.at(index)
  end
end
 
# An array with an odd amount of numbers
durations = [100,200,200,300,300,400,400,500,5_000]
 
percentile(durations, 20) #=> 100
percentile(durations, 90) #=> 500
percentile(durations, 95) #=> 5000, index is a fraction, 9.5 the rounded index is 10
 
# An array with an even amount of numbers
durations = [100,100,200,200,300,300,400,400,500,5_000]
 
percentile(durations, 20) #=> 150, average of index 1 & 2 `(100 + 200) / 2`
percentile(durations, 90) #=> 2750, average of index 8 & 9 `(500 + 5000) / 2
percentile(durations, 95) #=> 500, index is a fraction, 8.55 the index is 9

percentile này hàm trông rất giống với median của chúng tôi tính toán và trên thực tế, median giống với 50th phân vị.

durations = [1,2,3]
 
percentile(durations, 50) == median(durations) #=> true

AppSignal sử dụng số liệu thống kê ở trên để tạo chỉ số hiệu suất cho Ứng dụng của bạn. Chúng tôi không chỉ dựa vào giá trị trung bình / trung bình mà còn tính toán tỷ lệ phần trăm thứ 90 và 95 để chỉ ra các giá trị ngoại lệ mang lại ý tưởng tốt hơn về việc phân phối các yêu cầu của bạn. Tìm hiểu thêm trên trang tham quan hiệu suất của chúng tôi.

Kỳ lạ

Vì cách phân vị và trung bình được tính toán, đôi khi có thể có phân vị thứ 90 giảm xuống dưới mức trung bình, ví dụ, dựa trên tập dữ liệu sau:

durations = [1,1,1,1,1,1,1,1,1,1,2000]
 
percentile(durations, 90) #=> 1
mean(durations) #=> 182.73

Điều này sẽ cung cấp cho chúng tôi một median trong tổng số 182.73 và phân vị thứ 90 chỉ 1 .

Nếu hệ thống thu thập số liệu của bạn chỉ hiển thị phần trăm thứ 90 và giá trị trung bình, bạn vẫn có thể suy ra rằng có một sự chênh lệch lớn ở đâu đó trong tập dữ liệu của mình nếu phần trăm thứ 90 giảm xuống dưới mức trung bình.

👋 Nếu bạn thích bài viết này, chúng tôi đã viết nhiều hơn về hiệu suất của Ruby (trên Rails), hãy xem danh sách kiểm tra giám sát hiệu suất Ruby của chúng tôi.

Bạn gần như đọc hết 100% bài đăng này

Đó là nó cho bây giờ! Trong một bài đăng khác, chúng tôi sẽ nói về cách chúng tôi lưu trữ và tính toán các phần trăm một cách hiệu quả cho tất cả các yêu cầu của khách hàng bằng cách sử dụng Quantiles. Nếu bạn có bất kỳ câu hỏi hoặc nhận xét nào về số liệu thống kê và APM, theo dõi lỗi hoặc giám sát hiệu suất, hãy liên hệ với chúng tôi trên Twitter @AppSignal hoặc qua email.