消除 MARS 回归中的异常值

机器算法验证 r 回归 多重回归 异常值 火星
2022-04-11 01:34:23

我使用名为的回归方法MARSR它被称为earth并位于包earth中,以便为我的数据找到最佳回归模型。

我知道这种方法适用于大型数据集,可以处理NA并决定哪些变量将被使用,哪些不进入回归。

我在做什么

在估计回归后,我检测outliers使用boxplot ,然后从数据中消除观察结果extreme values并再次计算模型。

我这样做直到找到最大的grsqrsq

代码

model <- earth(log(price) ~ ., data = data, weights = weights)
max_grsq <- round(model$grsq, digits = 4)
    max_rsq <- round(model$rsq, digits = 4)
min_diff <- abs(max_grsq - max_rsq)

while(!done) {
  residuals_abs <- abs(model$residuals)
      boxplot <- boxplot(residuals_abs, plot=F)
      indexes_to_remove <- c(which((residuals_abs > boxplot$stats[4]) == T), which((residuals_abs < boxplot$stats[2]) == T))

  if (length(indexes_to_remove) > 0) {
    data <- data[-indexes_to_remove, ]
    distances <- distances[-indexes_to_remove]
    weights <- (1/distances)/(sum(1/distances))
  }

  tempModel <- earth(log(price) ~ ., data = data, weights = weights)
  temp_grsq <- round(tempModel$grsq, digits = 4)
      temp_rsq <- round(tempModel$rsq, digits = 4)
  temp_diff <- abs(temp_grsq - temp_rsq)

  if ((temp_grsq > max_grsq && temp_rsq >= max_rsq) || (temp_grsq >= max_grsq && temp_rsq > max_rsq)) {
    model <- tempModel
    max_grsq <- temp_grsq
    max_rsq <- temp_rsq
    min_diff <- temp_diff
  } else {
    done = T
  }
 }

问题

我不是统计学家,所以我不知道有什么更好的方法来去除异常值。

  • 我的方法正确吗?
  • 我应该使用另一种方法吗?
  • 我知道有坏异常值和好异常值(杠杆点),我怎样才能只删除坏异常值?
  • 我正在使用semi-log form回归的。因为dummy variables我不能使用log-log form. 有没有其他的数据转换方法?还是我应该标准化数据?x <- (x - x_min)/(x_max - x_min)

有人有一些提示吗?

3个回答

我的建议与使用的软件无关。

我们需要澄清异常值是 Y(因变量)中的异常值,还是预测变量 X 中的异常值。预测变量 X 中的异常值很容易通过大量可用的变换来处理,这些变换将重塑 PDF(概率密度函数) 的 X。

虽然我同意 Eric Farng 的观点,即不建议删除 Y 中的异常值,但我不同意他的观点,即只有在“仔细考虑”之后才应该删除它们。在我看来,永远不应该删除异常值,因为它们包含重要和有用的信息,也就是说,除非人们可以确定这些值在某种程度上是“坏的”、非法的或欺诈性的等。在 Y 中删除异常值的替代方法是利用建模对异常值具有鲁棒性的方法。

为什么我反对 Y 中的先验异常值删除?让我举个例子:在“仔细考虑”(Eric Farng 的措辞,但是人们选择定义它)之后,第一组异常值被删除。这是否意味着您已完成删除异常值?可能不会,因为第二次分析几乎肯定会揭示一组与新均值和标准差相关的新异常值。人们如何处理这些新信息?需要多少次数据才能完全清除异常值?显然,这是一个潜在的无休止的异常值删除过程,几乎没有意义。

最重要的是,甚至在人们进入是否删除异常值这一几乎是哲学问题之前,应该注意的是,MARS利用 X 和 Y 之间关系的非线性分位数函数的稳健的非参数替代方案之一。从纯粹应用和实际的角度来看,这意味着 MARS 非常健壮,几乎不受 Y 中异常值的影响:根据定义,在利用 MARS 时,删除 Y 中的异常值是不必要的,甚至没有实际意义。

R 包文档原始 MARS 论文中,它看起来像rsqgrsq用于包内的模型选择,并且看起来您的代码正在删除异常值,直到模型的拟合最大化。通常不建议这样做。有统计工具可以帮助识别潜在的异常值,并且只有在仔细考虑后才能删除异常值. 错误的点(计数数据的值为 -1)或不代表人口(包含儿童数据点的成年人人口)可以被删除。至于其他点,它们可能是一个不幸的异常值。他们也可能不幸只获得一分而不是更多。所以这些只有在仔细检查后才能删除。

earth包中,残差和杠杆很容易获得。正如您所说,并非所有高杠杆点都一定是问题。Cook's Distance试图通过从数据中实际删除该点并检查任何预测值如何变化来解决该问题。不幸的是,可能很难找到一个库来计算这个和其他支持该earth包的异常指标。但是,此软件包确实支持该plot(model)命令,该命令也会给出一些潜在的异常值。

对于log-log form,我相信您可以跳过分类变量,如果对于具有类别的变量,它们被表示为二进制/虚拟变量。例如,在简单的线性回归中,将分类虚拟变量 [0, 1] 转换为 [0, 0.5] 只会导致其系数翻倍。这是一个使用 MARS 回归的示例。是因变量。是自变量,其中是分类变量。在第二个示例中,分别从 (0 和 1) 更改为 (0 和 0.5) 和 (-1, 1)。nn1ab, d, edede

a <- rnorm(100)
b <- rexp(100) + a
c <- rgamma(100, shape=1) + 2*a
d <- sapply(sapply(round(b + c), function(x) min(1,x)), function(y) max(0, y))
e <- sapply(sapply(round(a - c), function(x) min(1,x)), function(y) max(0, y))
fit <- earth( a ~ b + d + e)

e2 <- e * 2
e2 <- e2 - 1
d2 <- d * 0.5
fit2 <- earth( a ~ b + d2 + e2)

summary(fit)
summary(fit2)
sum(predict(fit) - predict(fit2))

您可以从输出中看到,d、e 和截距的系数发生了变化,但其他系数均未发生变化。此外,模型之间的预测是相同的。

以供参考:

rsq=R2grsq=1gcvgcv.nullgcv=1Ni=1N[yif^M(xi)]2[1C(M)N]2C(M)=trace(B(BTB)1BT)+1

B是“数据”矩阵。是仅拦截模型的广义交叉验证。gcv.null

稍微详细说明 Eric Farng 的评论,即不建议在模型拟合最大化之前删除异常值:

调整数据直到获得良好的 GRSq 的根本问题是,尽管您将构建一个模型来很好地拟合您选择的数据,但您的模型不会对未来的数据做出良好的预测——因为您不是在建模数据的基本分布。它就像一个模型,对于历史数据可以非常准确地预测股票市场价格,但对于预测未来的股票价格却毫无用处。