解释插入符号序列中创建的虚拟变量

Interpreting dummy variables created in caret train

我通过阅读各种答案 1,2, 了解到,caret 中的 train 函数将创建虚拟变量来处理具有多个级别的因素。

这里是一个使用mtcars的例子(模型除了显示点外没有用):

library(caret)
library(rattle)

df <- mtcars

df$cyl <- factor(df$cyl)
df$mpg_bound <- ifelse(df$mpg > 20, "good", "bad")

tc <- trainControl(classProbs = TRUE, summaryFunction = twoClassSummary)

mod <- as.formula(mpg_bound ~ cyl)

set.seed(666)

m1 <- train(mod, data = df, 
            method = "rpart", 
            preProcess = c("center", "scale"),
            trControl = tc)

fancyRpartPlot(m1$finalModel)

m1$finalModel

n= 32 

node), split, n, loss, yval, (yprob)
      * denotes terminal node

1) root 32 14 bad (0.5625000 0.4375000)  
  2) cyl8>=0.124004 14  0 bad (1.0000000 0.0000000) *
  3) cyl8< 0.124004 18  4 good (0.2222222 0.7777778) *

这部分我没看懂cyl8>=0.124004。我知道 cyl8 是该因子的虚拟变量,但 cyl8>=0.124004 是什么意思?

我认为这个值表示基于虚拟变量比例 (0-1) 的分割点。此代码产生相同的结果:

df = mtcars

df$cyl <- factor(df$cyl)
df$mpg_bound <- ifelse(df$mpg > 20, "good", "bad")

tc <- trainControl(classProbs = TRUE, summaryFunction = twoClassSummary)

data = cbind(df,model.matrix(~cyl+mpg_bound,df)) # binds the dummy transf to the data

mod <- as.formula(mpg_bound ~ cyl8)

m1 <- train(mod, data = data, 
        method = "rpart", 
        preProcess = c("center", "scale"),
        trControl = tc)


m1$finalModel

直接 运行 rpart 代码(包括原始比例)可能更容易,尽管这可能不允许您指定您使用的功能。例如

 rpart(mpg_bound~cyl,data=df,method="class")

我想扩展现有的答案,因为我认为评论中得出的结论是不正确的。正如您所说,在使用公式界面时,caret 的 train 函数会将因子变量转换为仅取值 0 或 1 的虚拟变量,例如cyl8 == 1 表示 'the car has 8 cylinders'。每个虚拟变量都对一个特征进行了陈述,该特征对于观察结果是对还是错。
尽管如此,Rpart 还是会输出一个数值作为分割标准,因此 cyl8 >= 0.5、cyl8 >= 0.2 和 cyl8 == 1 都是同一个意思 "This car has exactly 8 cylinders"。默认情况下,rpart 将为二进制虚拟对象选择拆分值 cyl8 >= 0.5 以指示虚拟对象为真。 cyl8 >= 0.5 的解释是 "Does the car have 8 cylinders?" (并且 不是 "Does the car have more than 8 cylinders?")

df <- mtcars

df$cyl <- factor(df$cyl)
df$mpg_bound <- ifelse(df$mpg > 20, "good", "bad")

library(caret)
tc <- trainControl(classProbs = TRUE, summaryFunction = twoClassSummary)
set.seed(166)
m1 <- train(mod, data = df, 
        method = "rpart", 
        #preProcess = c("center", "scale"),
        trControl = tc,
        metric = "ROC")

m1$finalModel
   #1) root 32 14 bad (0.5625000 0.4375000)  
     #2) cyl8>=0.5 14  0 bad (1.0000000 0.0000000) *
     #3) cyl8< 0.5 18  4 good (0.2222222 0.7777778) *

你的例子中的混淆值是因为插入符号显然将预处理应用于扩展数据集,其中虚拟变量是数字变量。解释保持不变,但(任意)拆分值已转换。

# Transform to dummies
mm <- model.matrix(mpg_bound ~ .-1, data = df)

# Do pre-processing
pp <- preProcess(mm, method = c("center", "scale"))
mm.pp <- as.matrix(predict(pp, mm))

# Dummy-Split in the middle
(max(mm.pp[,"cyl8"]) + min(mm.pp[,"cyl8"]) ) / 2