R kullanarak zaman serilerinin STL trendi


27

Ben R ve zaman serileri analizinde yeniyim. Uzun (40 yıl) bir günlük sıcaklık süresi serisinin eğilimini bulmaya çalışıyorum ve farklı yaklaşımlar denedim. Birincisi sadece basit bir doğrusal regresyon ve ikincisi Loess'ın Time Serisinin Mevsimsel Ayrışması.

İkincisi, mevsimsel bileşen eğiliminden daha büyük olduğu görülmektedir. Fakat trendi nasıl ölçebilirim? Bu trendin ne kadar güçlü olduğunu söyleyen bir sayı istiyorum.

     Call:  stl(x = tsdata, s.window = "periodic")
     Time.series components:
        seasonal                trend            remainder               
Min.   :-8.482470191   Min.   :20.76670   Min.   :-11.863290365      
1st Qu.:-5.799037090   1st Qu.:22.17939   1st Qu.: -1.661246674 
Median :-0.756729578   Median :22.56694   Median :  0.026579468      
Mean   :-0.005442784   Mean   :22.53063   Mean   : -0.003716813 
3rd Qu.:5.695720249    3rd Qu.:22.91756   3rd Qu.:  1.700826647    
Max.   :9.919315613    Max.   :24.98834   Max.   : 12.305103891   

 IQR:
         STL.seasonal STL.trend STL.remainder data   
         11.4948       0.7382    3.3621       10.8051
       % 106.4          6.8      31.1         100.0  
     Weights: all == 1
     Other components: List of 5   
$ win  : Named num [1:3] 153411 549 365  
$ deg  : Named int [1:3] 0 1 1   
$ jump : Named num [1:3] 15342 55 37  
$ inner: int 2  
$ outer: int 0

görüntü tanımını buraya girin

Yanıtlar:


20

Bunun stl()için uğraşmazdım - eğilimi ortaya çıkarmak için kullanılan alçakgönüllü pürüzsüz bant genişliği gördüğünüz küçük çaplı dalgalanmalarla sonuçlanacak kadar uzak. Ek bir model kullanırdım. İşte Simon Wood'un GAM'lar kitabındaki verileri ve model kodunu kullanan bir örnek:

require(mgcv)
require(gamair)
data(cairo)
cairo2 <- within(cairo, Date <- as.Date(paste(year, month, day.of.month, 
                                              sep = "-")))
plot(temp ~ Date, data = cairo2, type = "l")

Kahire sıcaklık verileri

Trend ve mevsimsel bileşenlere sahip bir model takın --- bu yavaş olacaktır uyarısı :

mod <- gamm(temp ~ s(day.of.year, bs = "cc") + s(time, bs = "cr"),
            data = cairo2, method = "REML",
            correlation = corAR1(form = ~ 1 | year),
            knots = list(day.of.year = c(0, 366)))

Takılan model şöyle görünür:

> summary(mod$gam)

Family: gaussian 
Link function: identity 

Formula:
temp ~ s(day.of.year, bs = "cc") + s(time, bs = "cr")

Parametric coefficients:
            Estimate Std. Error t value Pr(>|t|)    
(Intercept)  71.6603     0.1523   470.7   <2e-16 ***
---
Signif. codes:  0 ‘***’ 0.001 ‘**’ 0.01 ‘*’ 0.05 ‘.’ 0.1   1 

Approximate significance of smooth terms:
                 edf Ref.df       F p-value    
s(day.of.year) 7.092  7.092 555.407 < 2e-16 ***
s(time)        1.383  1.383   7.035 0.00345 ** 
---
Signif. codes:  0 ‘***’ 0.001 ‘**’ 0.01 ‘*’ 0.05 ‘.’ 0.1   1 

R-sq.(adj) =  0.848  Scale est. = 16.572    n = 3780

ve trend ve mevsim terimlerini görselleştirebiliriz.

plot(mod$gam, pages = 1)

Kahire moda trendi ve mevsimlik

ve eğer gözlemlenen verilere olan eğilimi çizmek istiyorsak bunu aşağıdakilerle tahmin yaparak yapabiliriz:

pred <- predict(mod$gam, newdata = cairo2, type = "terms")
ptemp <- attr(pred, "constant") + pred[,2]
plot(temp ~ Date, data = cairo2, type = "l",
     xlab = "year",
     ylab = expression(Temperature ~ (degree*F)))
lines(ptemp ~ Date, data = cairo2, col = "red", lwd = 2)

Kahire hazır trendi

Veya gerçek model için aynı:

pred2 <- predict(mod$gam, newdata = cairo2)
plot(temp ~ Date, data = cairo2, type = "l",
     xlab = "year",
     ylab = expression(Temperature ~ (degree*F)))
lines(pred2 ~ Date, data = cairo2, col = "red", lwd = 2)

Kahire donanımlı model

Bu sadece bir örnektir ve daha derinlemesine bir analiz birkaç eksik veri olduğu gerçeğiyle başa çıkmak zorunda kalabilir, ancak yukarıdaki iyi bir başlangıç ​​noktası olmalıdır.

Eğilimin nasıl ölçüleceği konusundaki amacınıza gelince - bu bir problemdir, çünkü eğilim ne stl()sürümünüzde ne de GAM sürümünde gösterdiğim gibi doğrusal değildir . Öyle olsaydı, değişim oranını (eğim) verebilirdiniz. Örnekleme dönemi boyunca tahmini eğilimin ne kadar değiştiğini bilmek istiyorsanız, içerdiği verileri kullanabilir ve yalnızca trend bileşenindeki predserinin başlangıcı ile bitişi arasındaki farkı hesaplayabiliriz :

> tail(pred[,2], 1) - head(pred[,2], 1)
    3794 
1.756163

bu nedenle sıcaklıklar, kaydın başlangıcından ortalama olarak 1,76 derece daha sıcaktır.


Grafiğe baktığımda, Fahrenheit ve Celsius arasında bir karışıklık olabileceğini düşünüyorum.
Henry,

Benekliyim - Birkaç aydır benzer bir şey yapıyorum ve veriler derece C derecesinde.
Monica'yı yeniden kurgula - G. Simpson

Sağol Gavin, çok hoş ve anlaşılır bir cevap. Ben önerilerini deneyeceğim. Stl () trend bileşenini çizmek ve doğrusal bir regresyon yapmak iyi bir fikir midir?
pacomet

1
@ pacomet - hayır, gerçekten değil, yukarıda yaptığım gibi artıklarda otomatik korelasyonu hesaba katan bir modele uymazsanız. Bunun için gls()GLS'yi kullanabilirsiniz ( nlme paketinde). Ancak yukarıdakiler Kahire ve STL'nin verileriniz için önerdiği gibi, eğilim doğrusal değildir. Bu nedenle, doğrusal bir eğilim uygun olmaz - verileri düzgün bir şekilde tanımlamaz. Verilerinizde denemeniz gerekir, ancak gösterdiğim gibi bir AM, verileri en iyi şekilde karşılarsa doğrusal bir eğilime düşer.
Monica'yı yeniden kurun - G. Simpson,

1
@ andreas-h Bunu yapmazdım; STL trendi sona erdi. GAM'i AR () yapısına uygun hale getirin ve eğilimi yorumlayın. Bu sizin için çok daha faydalı olacak uygun bir regresyon modeli verecektir.
Monica'yı eski durumuna getirme - G. Simpson,

4

Gavin çok kapsamlı bir cevap sağlanan, ancak daha basit ve daha hızlı çözüm için, ben ayarlamanızı öneririz stl işlevi t.window katları olan bir değere parametre frekansı arasında ts verilerle. Çıkarılan faiz periyodikliğini kullanırdım (örneğin, günlük çözümleme verileriyle birlikte eski trendler için 3660 değeri). Ayrıca , yazarın tezinde açıklanan stl2 paketi ile de ilgilenebilirsiniz . Gavin'in yöntemini kendi verilerime uyguladım ve bu da çok etkili.

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.