(Jawaban ini menanggapi pertanyaan rangkap (sekarang ditutup) di Mendeteksi peristiwa luar biasa , yang menyajikan beberapa data dalam bentuk grafis.)
Deteksi outlier tergantung pada sifat data dan pada apa yang Anda anggap tentang mereka. Metode tujuan umum mengandalkan statistik yang kuat. Semangat dari pendekatan ini adalah untuk mengkarakterisasi sebagian besar data dengan cara yang tidak dipengaruhi oleh outlier dan kemudian menunjuk pada nilai-nilai individual yang tidak sesuai dengan karakterisasi tersebut.
Karena ini adalah deret waktu, ini menambah komplikasi karena perlu (kembali) mendeteksi pencilan secara berkelanjutan. Jika ini harus dilakukan saat seri dibuka, maka kami hanya diizinkan menggunakan data yang lebih lama untuk pendeteksian, bukan data mendatang! Selain itu, sebagai perlindungan terhadap banyak pengujian berulang, kami ingin menggunakan metode yang memiliki tingkat positif palsu yang sangat rendah.
Pertimbangan ini menyarankan menjalankan tes outlier jendela sederhana, kuat bergerak atas data . Ada banyak kemungkinan, tetapi yang sederhana, mudah dipahami dan diimplementasikan dengan mudah didasarkan pada MAD yang sedang berjalan: median deviasi absolut dari median. Ini adalah ukuran variasi yang sangat kuat dalam data, mirip dengan standar deviasi. Puncak terpencil akan menjadi beberapa MAD atau lebih besar dari median.
R
x = ( 1 , 2 , ... , n )n = 1150y
# Parameters to tune to the circumstances:
window <- 30
threshold <- 5
# An upper threshold ("ut") calculation based on the MAD:
library(zoo) # rollapply()
ut <- function(x) {m = median(x); median(x) + threshold * median(abs(x - m))}
z <- rollapply(zoo(y), window, ut, align="right")
z <- c(rep(z[1], window-1), z) # Use z[1] throughout the initial period
outliers <- y > z
# Graph the data, show the ut() cutoffs, and mark the outliers:
plot(x, y, type="l", lwd=2, col="#E00000", ylim=c(0, 20000))
lines(x, z, col="Gray")
points(x[outliers], y[outliers], pch=19)
Diterapkan ke dataset seperti kurva merah yang diilustrasikan dalam pertanyaan, ini menghasilkan hasil ini:
Data ditampilkan dalam warna merah, jendela 30 hari dari median + 5 * ambang batas MAD berwarna abu-abu, dan outlier - yang hanya berupa nilai data di atas kurva abu-abu - berwarna hitam.
(Ambang hanya dapat dihitung mulai dari akhir jendela awal. Untuk semua data di dalam jendela awal ini, ambang pertama digunakan: itu sebabnya kurva abu-abu datar antara x = 0 dan x = 30.)
Efek dari mengubah parameter adalah (a) meningkatkan nilai window
akan cenderung memuluskan kurva abu-abu dan (b) meningkatkan threshold
akan meningkatkan kurva abu-abu. Mengetahui hal ini, seseorang dapat mengambil segmen awal dari data dan dengan cepat mengidentifikasi nilai-nilai parameter yang paling baik memisahkan puncak-puncak terpencil dari sisa data. Terapkan nilai parameter ini untuk memeriksa sisa data. Jika plot menunjukkan metode semakin memburuk dari waktu ke waktu, itu berarti sifat data berubah dan parameter mungkin perlu disetel ulang.
Perhatikan betapa sedikitnya metode ini mengasumsikan tentang data: mereka tidak harus didistribusikan secara normal; mereka tidak perlu menunjukkan periodisitas apa pun; mereka bahkan tidak harus non-negatif. Semua itu mengasumsikan bahwa data berperilaku dengan cara yang hampir sama dari waktu ke waktu dan bahwa puncak terpencil tampak lebih tinggi daripada sisa data.
Jika ada yang ingin bereksperimen (atau membandingkan beberapa solusi lain dengan yang ditawarkan di sini), berikut adalah kode yang saya gunakan untuk menghasilkan data seperti yang ditunjukkan dalam pertanyaan.
n.length <- 1150
cycle.a <- 11
cycle.b <- 365/12
amp.a <- 800
amp.b <- 8000
set.seed(17)
x <- 1:n.length
baseline <- (1/2) * amp.a * (1 + sin(x * 2*pi / cycle.a)) * rgamma(n.length, 40, scale=1/40)
peaks <- rbinom(n.length, 1, exp(2*(-1 + sin(((1 + x/2)^(1/5) / (1 + n.length/2)^(1/5))*x * 2*pi / cycle.b))*cycle.b))
y <- peaks * rgamma(n.length, 20, scale=amp.b/20) + baseline