我是R.的新手。解决此数据集时遇到问题。
df
ID Time Value
1001 -34 3.3
1001 14 4.2
1002 -34 3.8
1002 14 6.5
1004 -18 4.1
1004 -11 3.4
1004 37 3.8
1005 -16 5.8
1005 -10 6.0
1005 14 8.1
1006 -20 16.1
1006 -10 14.1
1006 158 14.1
1007 -35 7.1
1007 -20 4.6
1007 -20 5.1
1007 10 5.0
对于每个ID,如果有一个以上读数为负时间,请将该值替换为均值,并将时间设置为0.结果数据集应为:
df1
ID Time Value
1001 0 3.3
1001 14 4.2
1002 0 3.8
1002 14 6.5
1004 0 3.75
1004 37 3.8
1005 0 5.9
1005 14 8.1
1006 0 15.1
1006 158 14.1
1007 0 5.6
1007 10 5.0
感谢您的帮助!
答案 0 :(得分:1)
如果您有大量数据,这将非常快。
#Convert to data.table object
require("data.table")
dt <- data.table(df)
#Label Negative values
dt[,Neg:=(Time<0)*1]
#Make positive and negative datasets
dt1 <- dt[Neg==0]
dt2 <- dt[Neg==1,list(Time=0,Value=mean(Value,na.rm=T),Neg=1),by="ID"]
#Recombine them together
df.final <- rbindlist(list(dt1,dt2))[order(ID,Time)]
结果如下
# ID Time Value Neg
# 1: 1001 0 3.30 1
# 2: 1001 14 4.20 0
# 3: 1002 0 3.80 1
# 4: 1002 14 6.50 0
# 5: 1004 0 3.75 1
# 6: 1004 37 3.80 0
# 7: 1005 0 5.90 1
# 8: 1005 14 8.10 0
# 9: 1006 0 15.10 1
# 10: 1006 158 14.10 0
# 11: 1007 0 5.60 1
# 12: 1007 10 5.00 0
您也可以将它们放在一个单行中,以获得如下类似的答案:
dt[, list(Time=Time[1] * tt,
Value = if(tt) Value else mean(Value)),
by=list(ID, tt=Time>0)]
答案 1 :(得分:1)
这是另一个解决方案。
#copy raw data
dx <- df
#find time<0
lz <- dx$Time<0
#set those to tim 0
dx$Time[lz] <- 0
#update means for each ID for those values where time<0
dx$Value[lz] <- ave(dx$Value, dx$ID, lz, FUN=mean)[lz]
#remove duplicated time<0 values
dx<- dx[!(duplicated(dd$ID, lz) & lz), ]
结果......
ID Time Value
1 1001 0 3.30
2 1001 14 4.20
3 1002 0 3.80
4 1002 14 6.50
5 1004 0 3.75
7 1004 37 3.80
8 1005 0 5.90
10 1005 14 8.10
11 1006 0 15.10
13 1006 158 14.10
14 1007 0 5.60
17 1007 10 5.00