R:e1071 svm函数-是否有必要将分类转换为虚拟变量?

时间:2020-05-13 19:10:38

标签: r machine-learning svm e1071

我知道svm模型需要进行预处理,以将分类变量转换为伪变量。但是,当我使用e1071的{​​{1}}函数拟合具有未转换数据的模型时(请参见svmtrain),不会弹出错误。我假设函数会自动将它们转换。

但是,当我使用转换后的数据(请参见testtrain2)来拟合svm模型时,此函数会给我带来不同的结果(如图所示,test2和{ {1}}不同)。

有人可以让我知道未转换的数据怎么了吗?函数是否只是忽略分类变量,还是发生了其他事情?

p1

2 个答案:

答案 0 :(得分:1)

从文档中可以明显看出,它的处理至少略有不同,因此注释“ 如果预测变量包含因子,则必须使用公式接口来获取正确的模型矩阵。 ”。

个人预感差异与缩放有关(svm中的默认值)。请注意...之间的区别。

> svm.model$x.scale$`scaled:center`
       X1        X2        X3        X4        X5 
10.091157  8.739654 10.395121  7.856475 11.660454 
> svm.model2$x.scale$`scaled:center`
        X1         X2         X3         X4         X5          A          B          C          D      X.NA. 
10.0911569  8.7396541 10.3951208  7.8564754 11.6604540  0.2000000  0.1333333  0.1333333  0.2333333  0.3000000 

答案 1 :(得分:1)

您所观察的确实是您所说的,虚拟变量是自动转换的。实际上,我们可以很容易地复制svm.model1svm.model2

mf <- model.frame(y ~ . - 1, train) # - 1 because the intercept is unused in svm.
mt <- terms(mf)
X <- model.matrix(mt, mf)
Xtest <- model.matrix(mt, test)
Y <- model.response(mf)
svm.model3 <- svm(X, Y)

请注意,我没有使用svm(formula, data),而是使用svm(x, y)。现在,我们实际上重新创建了哪种模型?让我们与p1p2

进行比较
all.equal(p1, predict(svm.model3, newdata = Xtest))
# [1] "Mean relative difference: 0.03064692"
all.equal(p2, predict(svm.model3, newdata = Xtest))
# [1] TRUE

似乎我们已经用手动虚拟模型重新创建了模型2。现在,之所以复制svm.model2而不是svm.model1的原因是由于scale参数。从help(svm)开始(请以粗体显示部分)

一个逻辑向量,指示要缩放的变量。 如果小数位数为1,则该值会根据需要回收多次。默认情况下,数据在内部(x和y变量)均按比例缩放为零均值和单位方差。返回中心和比例值,并用于以后的预测。

由此我们可以看出,可能的差异(实际上是问题)是由于svm不能正确地将二进制列标识为虚拟变量,但是显然足够聪明,可以在执行自动转换时执行此操作。我们可以通过手动设置scale参数

来测试该理论
#labels(mt) = 'cate', 'X1', 'X2', ... 
#names(attr(X, 'constrasts')) = 'cate' 
#eg: scale = Anything but 'cate'
not_dummies <- !(labels(mt) %in% names(attr(X, 'contrasts')))
n <- table(attr(X, 'assign'))
scale <- rep(not_dummies, n)
svm.model4 <- svm(X, Y, scale = scale)
all.equal(p1, predict(svm.model4, newdata = Xtest))
# [1] TRUE
all.equal(p2, predict(svm.model4, newdata = Xtest))
# [1] "Mean relative difference: 0.03124989"

所以我们看到的是

1)svm如所述,将因子自动转换为虚拟变量。

2)但是,如果提供了虚拟变量,则不要检查它们,如果手动创建它们,可能会导致意外行为。