我想做的是:按名称和类别排列数据,按年份排序,计算值的平均值,并保留valueMessage
。
样本数据:
name <- c("a", "a", "b", "b")
class <- c("c1", "c1", "c3", "c3")
year <- c("2010", "2010", "2008", "2008")
value <- c(100, 33, 100, 90)
valueMessage <-c(NA, "meh", NA, NA)
df <- data.frame(name, class, year, value, valueMessage)
df
dat <- aggregate(df$value, list(year = df$year, name = df$name, class=df$class, valueMessage=df$valueMessage), mean)
dat <- dat[with(dat, order(class, name, year)), ]
返回此:
year name class valueMessage x
1 2010 a c1 meh 33
但我希望它保留NA并返回如下内容:
year name class valueMessage x
1 2010 a c1 meh, NA 66.5
2 2008 b c3 NA 95
最佳答案
事实是,您正在尝试进行两种不同的聚合:一种用于“value”列,另一种用于“valueMessage”列。
如果是这样,您将必须分别进行每个操作并对其进行merge
编码,或者着眼于使用诸如“data.table”之类的包来提供帮助。
使用“data.table”,您可以执行以下操作:
library(data.table)
DT <- data.table(df)
DT[, list(value = mean(value),
valueMessage = list(unique(valueMessage))),
by = list(year, name, class)]
# year name class value valueMessage
# 1: 2010 a c1 66.5 NA,meh
# 2: 2008 b c3 95.0 NA
请注意,“valueMessage”列为
list
。如果希望将paste
用作字符向量,则可以使用aggregate
。换句话说:DT[, list(value = mean(value),
valueMessage = paste(unique(valueMessage), collapse = ",")),
by = list(year, name, class)]
在这里,我假设您只对唯一的“valueMessage”值感兴趣。
如果您想使用基数R的
as.character(valueMessage)
,则可以尝试以下操作:M1 <- aggregate(value ~ year + name + class, df, mean)
M2 <- aggregate(as.character(valueMessage) ~ year + name + class,
df, unique, na.action = na.pass)
merge(M1, M2)
我使用“公式”方法是因为我更喜欢输出。
factor
是必需的,因为该列目前是valueMessage
。 list
列的输出将再次是paste
,但是如果您更喜欢length
1的字符向量,则可以使用匿名函数和ojit_code。关于r - 汇总并保留不适用的行,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/24647832/