グループ化された時系列の遅延


10

時系列にはありますが場所ごとにグループ化された数万の観測があります。例えば:

location date     observationA observationB
---------------------------------------
 A       1-2010   22           12
 A       2-2010   26           15
 A       3-2010   45           16
 A       4-2010   46           27
 B       1-2010   167          48
 B       2-2010   134          56
 B       3-2010   201          53
 B       4-2010   207          42

私は月かどうかを確認したいのxさんは、observationA月との任意の線形の関係があるのx + 1つのをobservationB

私はいくつかの調査を行い、zoo関数を見つけましたが、グループごとの遅延を制限する方法がないようです。したがって、動物園を使用しobservationB、1行遅れている場合observationB、場所Bが最初になり、場所Aが最後になりますobservationB。私はむしろ、「この行に触れないでください」を示す最初observationBの場所NAまたは他の明白な値を設定したいと考えています。

私が得ているのは、Rでこれを行う組み込みの方法があるかどうかです。そうでない場合は、標準のループ構造でこれを実行できると思います。それともデータを操作する必要がありますか?

回答:


23

グループ内の遅延変数を取得する方法はいくつかあります。まず、データを並べ替える必要があります。これにより、各グループで時刻がそれに応じて並べ替えられます。

まず、サンプルのdata.frameを作成します。

> set.seed(13)
> dt <- data.frame(location = rep(letters[1:2], each = 4), time = rep(1:4, 2), var = rnorm(8))
> dt
  location time        var
1        a    1  0.5543269
2        a    2 -0.2802719
3        a    3  1.7751634
4        a    4  0.1873201
5        b    1  1.1425261
6        b    2  0.4155261
7        b    3  1.2295066
8        b    4  0.2366797

ラグ関数を定義します。

 lg <- function(x)c(NA, x[1:(length(x)-1)])
  1. 次に、グループ内の変数のラグを使用して計算できますtapply

     > unlist(tapply(dt$var, dt$location, lg))
        a1         a2         a3         a4         b1         b2         b3         b4 
        NA  0.5543269 -0.2802719  1.7751634         NA  1.1425261  0.4155261  1.2295066
    
  2. ddplyパッケージplyrからの使用:

    > ddply(dt, ~location, transform, lvar = lg(var))
      location time        var       lvar
    1        a    1 -0.1307015         NA
    2        a    2 -0.6365957 -0.1307015
    3        a    3 -0.6417577 -0.6365957
    4        a    4 -1.5191950 -0.6417577
    5        b    1 -1.6281638         NA
    6        b    2  0.8748671 -1.6281638
    7        b    3 -1.3343222  0.8748671
    8        b    4  1.5431753 -1.3343222  
    
  3. data.tableパッケージdata.tableを使用したより高速なバージョン

     > ddt <- data.table(dt)
     > ddt[,lvar := lg(var), by = c("location")]
         location time        var       lvar
    [1,]        a    1 -0.1307015         NA
    [2,]        a    2 -0.6365957 -0.1307015
    [3,]        a    3 -0.6417577 -0.6365957
    [4,]        a    4 -1.5191950 -0.6417577
    [5,]        b    1 -1.6281638         NA
    [6,]        b    2  0.8748671 -1.6281638
    [7,]        b    3 -1.3343222  0.8748671
    [8,]        b    4  1.5431753 -1.3343222
    
  4. lagパッケージplmの関数を使用する

     > pdt <- pdata.frame(dt)
     > lag(pdt$var)
       a-1        a-2        a-3        a-4        b-1        b-2        b-3        b-4 
        NA  0.5543269 -0.2802719  1.7751634         NA  1.1425261  0.4155261  1.2295066
    
  5. lagパッケージdplyrの関数を使用する

    > dt %>% group_by(location) %>% mutate(lvar = lag(var))        
    Source: local data frame [8 x 4]
    Groups: location        
      location time        var       lvar
    1        a    1  0.5543269         NA
    2        a    2 -0.2802719  0.5543269
    3        a    3  1.7751634 -0.2802719
    4        a    4  0.1873201  1.7751634
    5        b    1  1.1425261         NA
    6        b    2  0.4155261  1.1425261
    7        b    3  1.2295066  0.4155261
    8        b    4  0.2366797  1.2295066
    

最後の2つのアプローチではdata.frame、別のオブジェクトへの変換が必要ですが、ソートについて心配する必要はありません。私の個人的な好みは最後のもので、最初に答えを書いたときには利用できませんでした。

更新: data.tableコードを変更して、@ Hibernatingが指摘するdata.tableパッケージの開発を反映しました。

更新2:dplyrの例を追加しました。


素晴らしい説明!不規則な間隔でグループ化された時系列(パネル)と不均衡なパネルを処理できるパッケージ/関数はありますか?
Helix123 2016年

すべてのコード例は、不均衡なパネルで機能します。不規則な間隔の時系列の場合、ラグの概念は少し複雑です。ラグがすべてのグループに存在するとは限らないためです。
mpiktas 2016年

Stackoverflowの不規則な時系列のラグについて質問できます。これらのタイプの質問は、stats.SEでトピックから外れました。
mpiktas 2016年

2

@ mpiktas回答のバージョン3の2つの小さな見落としについて簡単に説明します。第一に、「より高速なバージョン」という語句は明らかに誤って残されています。次に、「:=」という単語がコードから抜けています。後者を修正すると、前者も修正されます:=)

library(data.table);ddt <- data.table(dt)
f0<-function() plyr::ddply(dt,~location,transform,lvar=lg(var))
f1<-function() ddt[,transform(.SD,lvar=lg(var)),by=c("location")]
f2<-function() ddt[,lvar:=lg(var),by=location]
r0<-f0();r1<-f1();r2<-f2();all.equal(r0,r1,r2,check.attributes = FALSE)
boxplot(microbenchmark::microbenchmark(f0(),f1(),f2(),times=1000L))

ここに画像の説明を入力してください


2

すべてのtapply追加手順を実行するよりも、こちらの方が速い方法です。

dt<-data.frame(location=rep(letters[1:2],each=4),time=rep(1:4,2),var=rnorm(8))
lg<-function(x)c(NA,x[1:(length(x)-1)])
dt$lg <- ave(dt$var, dt$location, FUN=lg)



0

DataCombineの場合:

library(DataCombine)
slide(df, Var="observationB", TimeVar="date", GroupVar="location", NewVar="lead.observationB", 
slideBy = 1, keepInvalid = FALSE, reminder = FALSE)

データもソートする必要があります。slideBy=-1ラグの代わりに使用してください。

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.