随机森林中的低解释方差(R randomForest)

机器算法验证 r 回归 随机森林 r平方
2022-04-12 09:34:23

我在 R 中使用 randomForest 进行回归,我有许多分类预测变量(它们都有相同的 3 个类别 (0,1,2)),我想看看它们中的哪一个可以预测响应(连续)。我正在尝试使用许多不同的响应变量(当时一个),并且所有模型的解释方差都非常低(基本上为 0,几乎总是负数)。

我检查了变量对之间的卡方并删除了可能关联的变量(p 值 < 0.05),但结果是相同的。

我的问题是:

1 - 这可能吗?我在没有注意到的情况下做错了什么吗?如果不:

2 - 在随机森林中,我必须扔掉所有东西还是我仍然可以使用变量重要性对预测变量进行分类?(我不这么认为,但由于我找不到任何关于此的内容,我仍然希望我能从中得到一些东西 - 顺便说一句,为什么预测的情节与观察到的情节看起来不错??)。如果不:

3 - 有什么建议吗?也适用于替代方法?

在下面的示例中,为了简单起见,我没有在训练和测试中划分数据,但我在我的代码中这样做了——同样的问题。此外,我的原始数据集要大得多(> 500 个观察值和近 100 个预测变量)

## predictors
> pred
   X1 X2 X3 X4 X5 X6 X7 X8 X9 X10 X11 X12 X13 X14 X15 X16 X17 X18 X19 X20
1   0  0  0  0  0  0  0  0  0   0   0   0   0   0   0   0   0   0   0   0
2   0  1  2  2  2  0  1  2  0   0   1   0   0   1   1   2   2   1   1   2
3   0  1  0  2  2  1  1  2  1   1   2   1   0   0   1   2   2   2   0   0
4   0  0  1  1  1  1  1  1  1   1   1   1   0   0   2   0   2   2   0   1
5   0  1  1  2  2  0  1  2  2   1   2   0   0   0   1   1   0   2   0   1
6   1  1  0  2  2  1  1  1  2   1   0   1   0   1   1   2   2   2   1   2
7   0  1  1  1  1  1  2  1  2   1   2   1   0   1   1   2   1   2   1   1
8   0  1  2  1  0  1  0  2  1   1   1   2   0   0   1   2   1   2   1   2
........

## response
> resp

[1]  19.416  46.058  39.496  79.752 301.012 746.377 277.721  13.922  15.598  82.195  86.263
[12]  82.522  30.829 101.369  31.496  39.366 133.510

## find optimal value of mtry for randomForest
> bestmtry <- tuneRF(pred, resp, ntreeTry=100,
+                    stepFactor=1.5,improve=0.01, trace=F, plot=F, dobest=FALSE)

## extract optimal value of mtry for randomForest
> ind <- as.numeric(names(which.min(bestmtry[,2])))

## Random Forest
> RF <-randomForest(pred, , y = resp, mtry=ind, ntree=500,
+ keep.forest=TRUE, importance=TRUE)

> RF

Call:
     randomForest(x = pred, y = resp, ntree = 500, mtry = ind, importance = TRUE,          keep.forest = TRUE) 
               Type of random forest: regression
                     Number of trees: 500
No. of variables tried at each split: 9

          Mean of squared residuals: 32713.86
                    % Var explained: -6.5

## Low explained variance (pseudo - r sqaured)

> RF.pr = predict(RF,pred)

## the plot isn't that bad though... it is if I use the test data set though
> plot(RF.pr, resp)
> abline(c(0,1),col=2)

在此处输入图像描述

> varImpPlot(RF)

在此处输入图像描述

我已经坚持了一段时间了......非常感谢任何帮助

1个回答

编辑回复*

一些可能会推动一点信号的变化......

缩放:RF 仅缩放不变的特征而不是响应。RFreg 使用均方误差作为损失函数,使用 CV 平方残差来评估性能。尝试对您的响应取对数或平方根,以降低少数“异常值”的杠杆率。

过滤:使用 randomForest 中的函数 rfcv 来选择变量。否则,线性滤波器可能有用。

共线性过滤:“我检查了变量对之间的卡方并删除了可能关联的变量(p 值 < 0.05),但结果是相同的。 ” - 不要使用特定的 p 值阈值 < 0.05 . 通过任何相似性度量使用任何阈值,使您的模型工作(CV 性能)。你删除了这对的两个成员吗?

可变重要性:不应该信任损坏模型的可变重要性。

评估射频性能:射频是否适合它自己的训练集是无关紧要的。RFreg 的树几乎生长到最大深度,并且会过拟合训练集。只能使用交叉验证(分段、OOB、nFold 等)来评估性能。以下代码显示了如何计算 %var 解释以及如何进行 OOB 预测。

library(randomForest)
obs = 500
vars = 100
X = replicate(vars,factor(sample(1:3,obs,replace=T)))
y = rnorm(obs,sd=5)^2

RF = randomForest(X,y,importance=T,ntree=20,keep.inbag=T)

#var explained printed
print(RF)
cat("% Var explained: \n", 100 * (1-sum((RF$y-RF$pred   )^2) /
                                    sum((RF$y-mean(RF$y))^2)
                                  )
   )

#how out-of-bag predicted values are formed 
#matrix of i row obs with j col predictions from j trees
allTreePred = predict(RF,X,predict.all=T)$individual 
#for i'th sample take mean of those trees where i'th sample was OOB (inbag==0)
OOBpred = sapply(1:obs,function(i) mean(allTreePred[i,RF$inbag[i,]==0]))

#we can see the values are the same +/- float precision
hist(OOBpred-RF$predicted)

#if using RF to predict it's own training data
Ypred = predict(RF,X)

#any obs (i) will be present in ~0.62 of the nodes and influence it's own
#prediction value. Therefore does the following prediction plot falsely
#look promising
    par(mfrow=c(1,2),mar=c(4,4,3,3))
    ylims=range(c(pred,OOBpred))
    plot(y   ,Ypred,ylim=ylims,main=paste("simple pred \n
                                         R^2=" ,round(cor(y,Ypred  ),2)))
    plot(y,OOBpred,ylim=ylims,main=paste("OOB prediction \n
                                         R^2=" ,round(cor(y,OOBpred),2)))

在此处输入图像描述