按组子集面板数据

时间:2015-03-31 19:15:34

标签: r panel subset

我想按组分组不平衡的面板数据集。对于每个小组,我想在第一年和最后几年保留这两个观察结果。

我如何在R中做到最好?例如:

dt <- data.frame(name= rep(c("A", "B", "C"), c(3,2,3)), 
                 year=c(2001:2003,2000,2002,2000:2001,2003))

> dt
  name year
1    A 2001
2    A 2002
3    A 2003
4    B 2000
5    B 2002
6    C 2000
7    C 2001
8    C 2003

我想拥有什么:

  name year
1    A 2001
3    A 2003
4    B 2000
5    B 2002
6    C 2000
8    C 2003

3 个答案:

答案 0 :(得分:2)

应该有所帮助。查看第一个()&amp; last()获取您要查找的值,然后根据这些值进行过滤。

dt <- data.frame(name= rep(c("A", "B", "C"), c(3,2,3)), year=c(2001:2003,2000,2002,2000:2001,2003))

library(dplyr)

dt %>%
  group_by(name) %>%
  mutate(first = first(year)
        ,last = last(year)) %>%
  filter(year == first | year == last) %>%
  select(name, year)

  name year
1    A 2001
2    A 2003
3    B 2000
4    B 2002
5    C 2000
6    C 2003

*你的例子没有提到任何具体的订单但是那个案例,arrange()会有所帮助

答案 1 :(得分:2)

这是一个快速data.table解决方案

library(data.table)
setDT(dt)[, .SD[c(1L, .N)], by = name]
#    name year
# 1:    A 2001
# 2:    A 2003
# 3:    B 2000
# 4:    B 2002
# 5:    C 2000
# 6:    C 2003

或者如果您只有两列

dt[, year[c(1L, .N)], by = name]

答案 2 :(得分:1)

使用by按组拆分data.frame然后返回每个组的头部和尾部非常简单。

> do.call(rbind, by(dt, dt$name, function(x) rbind(head(x,1),tail(x,1))))
    name year
A.1    A 2001
A.3    A 2003
B.4    B 2000
B.5    B 2002
C.6    C 2000
C.8    C 2003

headtail很方便,但速度很慢,因此在大型data.frame上可能会有更快的替代方案:

do.call(rbind, by(dt, dt$name, function(x) x[c(1,nrow(x)),]))