我有一个包含两个变量的数据集,一个是分组变量,另一个是值。数据按每组内的值排序。我想将值变量切换为每个组中的一个因子,并且小于diff(10)的间隔。也就是说,如果diff(val)> = 10,则创建新级别。下面是一个演示数据,其中newgrp
是我想要的新变量。也许filter()
在这里是可取的,但我已经对它发呆了很长一段时间。有什么想法吗?
grp val newgrp
a 101 1
a 101 1
a 102 1
a 110 1
a 111 2 <-- a new level is created since 111 - 101 > 9
a 112 2
a 148 3 <-- a new level is created sine 152 - 148 > 9,
a 157 3
a 158 4 <-- a new level is created since 158 - 148>9
b 8 1 <-- levels start over for group b
b 9 1
b 12 1
b 17 1
b 18 2
答案 0 :(得分:0)
修改强>
我认为没有办法避免首先定义一个循环遍历每个向量的函数,因为每次遇到足够大的差异时需要重置两个数字(“base”和“new group”)
NewGroup = function(x)
{
base = x[1]
new = 1
newgrp = c()
for(i in seq_along(x))
{
if (x[i] - base > 9)
{
base = x[i]
new = new + 1
}
newgrp[i] <- new
}
return(newgrp)
}
dt[,newgrp:=NewGroup(val),by=grp]
grp val newgrp
1: a 101 1
2: a 101 1
3: a 102 1
4: a 110 1
5: a 111 2
6: a 112 2
7: a 148 3
8: a 157 3
9: a 158 4
10: b 8 1
11: b 9 1
12: b 12 1
13: b 17 1
14: b 18 2
答案 1 :(得分:0)
您可以使用:
do.call(rbind, by(yourdf, yourdf$grp, function(df) within(df, newgrp <- cumsum(c(1,diff(val))>9))))
将yourdf
替换为您的数据框。