2016-04-21 25 views
1

嗨我有面板數據,並希望刪除任何只有一個觀察時間點的個人,並保持有2個時間點的觀察。刪除ID:s只有一個觀察時間r

所以數據幀:

df <- data.frame(id = c(1,2,2,3,3,4,4,5,6), time = c(1,1,2,1,2,1,2,2,2)) 

    id time 
1 1 1 
2 2 1 
3 2 2 
4 3 1 
5 3 2 
6 4 1 
7 4 2 
8 5 2 
9 6 2 

變成這樣:

id time 
1 2 1 
2 2 2 
3 3 1 
4 3 2 
5 4 1 
6 4 2 

即移除個別1,5和6,以使面板balansed。 Thx

回答

2

我們可以使用一些選項來做到這一點。使用data.table,將'data.frame'轉換爲'data.table'(setDT(df)),按'id'分組,得到大於1的行數(.N)和if,獲取Data.table的子集(.SD

library(data.table) 
setDT(df)[, if(.N>1) .SD, by = id] 
# id time 
#1: 2 1 
#2: 2 2 
#3: 3 1 
#4: 3 2 
#5: 4 1 
#6: 4 2 

可以使用相同的方法與dplyr

library(dplyr) 
df %>% 
    group_by(id) %>% 
    filter(n()>1) 
# id time 
# (dbl) (dbl) 
#1  2  1 
#2  2  2 
#3  3  1 
#4  3  2 
#5  4  1 
#6  4  2 

或者與base R,得到data.frame的table,檢查它是否大於1,基於邏輯指數(「I1」)子集names並用它來subset了「 data.frame'使用%in%

i1 <- table(df$id)>1 
subset(df, id %in% names(i1)[i1]) 
+1

大基地的解決方案! :) – Sotos

+1

使用data.table解決方案,完美的作品!非常感謝! –

0

您可以使用dplyr包來完成

library(dplyr) 
    df %>% group_by(id,time) %>% summarize(count = n()) %>% 
      filter(!count == 1) 
1

另一種選擇,

ind <- rle(df$id)$values[rle(df$id)$lengths > 1] 
df[df$id %in% ind,] 
# id time 
#2 2 1 
#3 2 2 
#4 3 1 
#5 3 2 
#6 4 1 
#7 4 2 
+2

您可能必須指定'id'是有序的 – akrun

1
library(data.table) 
setDT(df, key = "id")[(duplicated(id) | duplicated(id, fromLast = TRUE))] 
# id time 
#1: 2 1 
#2: 2 2 
#3: 3 1 
#4: 3 2 
#5: 4 1 
#6: 4 2