我有一个交易数据的数据集,如下所示:
prodid priceperitem date
62420 18.9 2014-10-09
62420 29.9 2014-09-20
62420 18.9 2014-10-11
62420 27.9 2014-07-04
62420 18.9 2014-08-25
62420 18.9 2014-11-01
我想删除每种产品的价格异常值。
我尝试了以下代码,并且将每个产品的价格都用NA代替了离群值。但这是一个单独的列表,并按prodid分组,我希望data变量保留在数据框中,而不要有一个新列表。
remove.outliers <- tapply(priceperitem, prodid, function(x) {
qnt <- quantile(x, probs=c(.25, .75))
H <- 1.5 * IQR(x)
y <- x
y[x < (qnt[1] - H)] <- NA
y[x > (qnt[2] + H)] <- NA
y
})
这段代码将为我提供如下输出:
$205780229
[1] NA 10.9 10.5 10.9 10.9 NA ....
这是一个新数组,但我想要的是以下内容:
prodid priceperitem date
205780229 NA 2014-10-03
205780229 10.9 2014-10-20
205780229 10.5 2014-10-30
205780229 10.9 2014-5-23
205780229 10.9 2014-11-20
....
您可以使用该by
函数以便将数据帧分为较小的子集,然后在各个子组上执行函数调用。在这些函数调用期间,您可以轻松地从每个子集中删除异常值并返回结果。接下来,您可以通过将子结果合并在一起来获得结果数据框。
我将使用以下数据框来举例说明:
prodid <- c(rep(62420,5),rep(62421,5))
pricePerItem <- c(18,18.1,23,17.9,18.0,51.7,22,51,52,52.2)
dates <- rep(Sys.time(),10)
products <- data.frame(prodid,pricePerItem,dates)
products
prodid pricePerItem dates
1 62420 18.0 2015-07-06 01:51:31
2 62420 18.1 2015-07-06 01:51:31
3 62420 23.0 2015-07-06 01:51:31
4 62420 17.9 2015-07-06 01:51:31
5 62420 18.0 2015-07-06 01:51:31
6 62421 51.7 2015-07-06 01:51:31
7 62421 22.0 2015-07-06 01:51:31
8 62421 51.0 2015-07-06 01:51:31
9 62421 52.0 2015-07-06 01:51:31
10 62421 52.2 2015-07-06 01:51:31
我们将数据帧分组,prodid
并过滤掉相关的异常值。我们通过合并结果来完成:
result <- by(products,products$prodid,function(product) {
qnt <- quantile(product$pricePerItem, probs=c(.25, .75))
H <- 1.5 * IQR(product$pricePerItem)
outlierCheck <- (product$pricePerItem) > qnt[1]-H & (product$pricePerItem<qnt[2]+H)
noOutliers <- product[outlierCheck,]
})
filteredFrame <- do.call("rbind",result)
filteredFrame
prodid pricePerItem dates
62420.1 62420 18.0 2015-07-06 01:51:31
62420.2 62420 18.1 2015-07-06 01:51:31
62420.4 62420 17.9 2015-07-06 01:51:31
62420.5 62420 18.0 2015-07-06 01:51:31
62421.6 62421 51.7 2015-07-06 01:51:31
62421.8 62421 51.0 2015-07-06 01:51:31
62421.9 62421 52.0 2015-07-06 01:51:31
62421.10 62421 52.2 2015-07-06 01:51:31
小编辑我注意到您想用一个NA
值替换离群值,而不是完全删除它们。您显然可以通过类似的方式来完成此行为。例如:
result <- by(products,products$prodid,function(product) {
qnt <- quantile(product$pricePerItem, probs=c(.25, .75))
H <- 1.5 * IQR(product$pricePerItem)
outliers <- (product$pricePerItem) < qnt[1]-H | (product$pricePerItem > qnt[2]+H)
product[outliers,2] <- NA
product
})
filteredFrame <- do.call("rbind",result)
filteredFrame
prodid pricePerItem dates
62420.1 62420 18.0 2015-07-06 02:14:06
62420.2 62420 18.1 2015-07-06 02:14:06
62420.3 62420 NA 2015-07-06 02:14:06
62420.4 62420 17.9 2015-07-06 02:14:06
62420.5 62420 18.0 2015-07-06 02:14:06
62421.6 62421 51.7 2015-07-06 02:14:06
62421.7 62421 NA 2015-07-06 02:14:06
62421.8 62421 51.0 2015-07-06 02:14:06
62421.9 62421 52.0 2015-07-06 02:14:06
62421.10 62421 52.2 2015-07-06 02:14:06
本文收集自互联网,转载请注明来源。
如有侵权,请联系[email protected] 删除。
我来说两句