从列标记每个组中最后一个元素的组索引

时间:2016-01-09 21:27:15

标签: r

我正在尝试对数据框进行子集化。数据帧将被分成子集,其中每个子集中的最后一个元素在“bool”列中具有“TRUE”值。请考虑以下数据框:

df <- data.frame(c(3,1,3,4,1,1,4), rnorm(7))
df <- cbind(df, df[,1] != 1)
names(df) <- c("ind", "var", "bool")
df
#   ind         var  bool
# 1   3  0.02343906  TRUE
# 2   1  0.94786193 FALSE
# 3   3  0.50632766  TRUE
# 4   4  0.24655548  TRUE
# 5   1 -1.58103304 FALSE
# 6   1  0.73999468 FALSE
# 7   4  0.10929906  TRUE

第1行应该是子集,第2行和第3行应该是子集,第4行应该是子集,然后第5行到第7行是子集。我在下面的代码工作(我可以在新列上进行子集),但我想知道是否有更“R”的方式。

index = 1
for (i in 1:nrow(df))
 {
  if(df$bool[i])
   {df$index[i] = index
    index = index + 1
   }
  else
  {df$index[i] = index
  }
}
df
#   ind         var  bool index
# 1   3  0.02343906  TRUE     1
# 2   1  0.94786193 FALSE     2
# 3   3  0.50632766  TRUE     2
# 4   4  0.24655548  TRUE     3
# 5   1 -1.58103304 FALSE     4
# 6   1  0.73999468 FALSE     4
# 7   4  0.10929906  TRUE     4

1 个答案:

答案 0 :(得分:1)

我首先想到的是使用cumsum列上的累积和(bool)来获取组索引 - 这将使每次{的索引值增加1 {1}}值为bool

TRUE

这不太正确,因为每组df$index <- cumsum(df$bool) df # ind var bool index # 1 3 -1.0712125 TRUE 1 # 2 1 0.4994369 FALSE 1 # 3 3 2.1335274 TRUE 2 # 4 4 -1.5950432 TRUE 3 # 5 1 0.5919880 FALSE 3 # 6 1 2.7039831 FALSE 3 # 7 4 -1.3526646 TRUE 4 之前的所有观察都被分配给前一组。我们可以通过为TRUE设置为bool的所有观察结果添加1来解决此问题:

FALSE

现在可以使用df$index <- cumsum(df$bool) + !df$bool df # ind var bool index # 1 3 -1.0712125 TRUE 1 # 2 1 0.4994369 FALSE 2 # 3 3 2.1335274 TRUE 2 # 4 4 -1.5950432 TRUE 3 # 5 1 0.5919880 FALSE 4 # 6 1 2.7039831 FALSE 4 # 7 4 -1.3526646 TRUE 4 有效地将数据框拆分为子集列表。