2017-08-24 4 views
3

これまでにないほどのデータ管理で新しいプロジェクトを開始しました。適切な検索用語を使用して例を見つけることができます。私はグループ化変数とバイナリイベント変数を持つ非常に大きなデータセットを持っています。私は新しい序数値要因「イベント」のイベントとして、「GRP」のユニークなレベル内の「V1」のラベル筋にdata.tableを使用してきた元の因子レベルの "N"回の連続した出現に基づいて、新しい因子/変数を作成する

library('data.table') 
grp <- c("a", "a", "a", "a", "a", "a", "a", "b", "b", "b", "b", "b") 
v1 <- c(1, 0, 0, 1, 1, 1, 1, 1, 0, 0, 0, 1) 
test<-data.frame(grp,v1) 
test 

    grp v1 
1 a 1 
2 a 0 
3 a 0 
4 a 1 
5 a 1 
6 a 1 
7 a 1 
8 b 1 
9 b 0 
10 b 0 
11 b 0 
12 b 1 

:次のように実施例に一般化することができる

これらの「GRP」特定のイベントのいくつかを設定し、実際のデータで
setDT(test) 
test<-test[, .(v1 = v1, event = rleidv(v1)), by=grp] 

    grp v1 event 
1: a 1  1 
2: a 0  2 
3: a 0  2 
4: a 1  3 
5: a 1  3 
6: a 1  3 
7: a 1  3 
8: b 1  1 
9: b 0  2 
10: b 0  2 
11: b 0  2 
12: b 1  3 

は非常に長く、私が小さい、変数、n個にそれらを分割する必要がある - 制限されたイベント。例えば、N = 2で新しい変数「sub.event」のための私の所望の出力は次のようになります。

> test 
    grp v1 event sub.event 
1: a 1  1   1 
2: a 0  2   2 
3: a 0  2   2 
4: a 1  3   3 
5: a 1  3   3 
6: a 1  3   4 
7: a 1  3   4 
8: b 1  1   1 
9: b 0  2   2 
10: b 0  2   2 
11: b 0  2   3 
12: b 1  3   4 

私はこれを行う方法を把握しようとしている私の髪を引っ張ってきました。それは私が明らかに何かを欠いているに違いないほど簡単です。容易にするために、元の変数を新しい変数に連結してからn -limited "sub.event"を決定することができます。

ご協力いただきありがとうございます。

答えて

3

ここでは、連鎖を使用する方法があります。

setDT(test)[, new := rep(1:0, length.out=.N), by=.(grp, rleid(v1))][, 
       new := cumsum(new), by=grp] 

第一鎖はgrp- rleid対の長さを繰り返す1と0のベクトルを返します。チェーン内の次のリンクはgrpによってcumsumでこれを合計します。

この

test 
    grp v1 new 
1: a 1 1 
2: a 0 2 
3: a 0 2 
4: a 1 3 
5: a 1 3 
6: a 1 4 
7: a 1 4 
8: b 1 1 
9: b 0 2 
10: b 0 2 
11: b 0 3 
12: b 1 4 

書かれたように、それが自動的にN> 2まで延びていないことに注意してください。しかし、それを生成ピース、1:0n+1が繰り返される値の数であるrep(c(1L, rep(0L, n)), length.out=.N)を書くことができるが返さあなたが望むだろう。

は、この場合、コードは

test[, new := rep(c(1L, rep(0L, 2L)), length.out=.N), by=.(grp, rleid(v1))][, 
     new := cumsum(new), by=grp] 
+0

おかげで多くのことを、今朝これらの両方を試してみるつもり。 –

+0

この場合、* n *を変更するという利便性が好きです。それは警告の束をキックバックします。私はdata.tableを学んでいるだけですが、 "イベント"サブグループが指定された "n"で割り切れず、残っている文字列が破棄されていると思いますか? –

+1

例のデータでは、* n *を小数または大きい数値に設定することができます。警告は表示されません。 1、2、12を試してみました。 'rep'ベクトルの最終的な長さは' length.out'によって制御されます。これはグループの長さに設定されます。 – lmo

2

やや遠回りのようになります。

# make counters within v1, grp 
test[, v0 := rep(1:.N, each=2, length.out=.N), by=.(rleid(grp, v1))] 

# make overall counters 
test[, v := .GRP, by=rleid(grp, v1, v0)] 

# difference per grp 
test[, v := v - first(v) + 1L, by=grp] 

# drop internal counter 
test[, v0 := NULL ] 

    grp v1 v 
1: a 1 1 
2: a 0 2 
3: a 0 2 
4: a 1 3 
5: a 1 3 
6: a 1 4 
7: a 1 4 
8: b 1 1 
9: b 0 2 
10: b 0 2 
11: b 0 3 
12: b 1 4 
+1

ありがとう、今日のこれらの両方を試してみよう。 –

関連する問題