Порядок изменения переменных в оценочных коэффициентах в glmnet

Я работаю с пакетом glmnet в R и столкнулся с проблемой при попытке воспроизвести "старый" классификатор. Если независимые переменные переставляются (скажем, в обратном порядке), результирующие коэффициенты из cv.glmnet не равны коэффициентам, использующим неизменяемую матрицу плана.

Например, рассмотрим следующие данные:

library(glmnet)
set.seed(1)

#Set initial parameters
n <- 100
p <- 1000

#Simulate data
x <- matrix(rnorm(n * p), nrow = n, ncol = p)
colnames(x) <- as.character(1:p)
beta <- rnorm(n = p, mean = 2, sd = 2)
beta[rbinom(p, size = 1, prob = 0.5) == 0] <- 0
y <- x %*% beta + rnorm(100, sd = 0.1)

Затем запустите glmnet со штрафом LASSO (альфа = 1) как для матрицы плана x, так и для измененной версии x.

#Set parameters for cross validation with cv.glmnet
lambda <- exp(seq(-1, 1, length.out = 100))
alpha <- 1
foldid <- rep(1:10, each = 10)

#Run cross validation
fit <- cv.glmnet(x = x, y = y, family = "gaussian", alpha = alpha, 
                 lambda = lambda, 
                 foldid = foldid)

#Save coefficients
coef1 <- as.matrix(coef(fit, s = "lambda.min"))

#Run cross validation with rearranged design matrix
order <- ncol(x):1
fit2 <- cv.glmnet(x = x[,order], y = y, family = "gaussian", alpha = alpha, 
                  lambda = lambda, 
                  foldid = foldid)

#Save coefficients
coef2 <- as.matrix(coef(fit2, s = "lambda.min"))
coef2 <- coef2[rownames(coef1),]

Затем сравните коэффициенты, ошибку перекрестной проверки и линейные предикторы.

> summary(coef2 - coef1)
       1             
 Min.   :-0.2738963  
 1st Qu.: 0.0000000  
 Median : 0.0000000  
 Mean   : 0.0003739  
 3rd Qu.: 0.0000000  
 Max.   : 0.3643040

> min(fit$cvm)
[1] 4584.373
> min(fit2$cvm)
[1] 4596.626

> summary(cbind(1,x) %*% coef2 - cbind(1, x) %*% coef1)
       1          
 Min.   :-0.5100  
 1st Qu.:-0.1613  
 Median : 0.0210  
 Mean   : 0.0000  
 3rd Qu.: 0.1333  
 Max.   : 0.6139

Для всех трех показателей мы видим разницу между моделями, хотя был изменен только порядок переменных. Кто-нибудь может это объяснить?


person Lasse Hjort Jakobsen    schedule 22.06.2016    source источник


Ответы (2)


Glmnet вычисляет пути регуляризации LASSO посредством спуска координат (см., Например, слайд 15 этого выступления Тревора Хасти: http://web.stanford.edu/~hastie/TALKS/glmnet.pdf). Поскольку алгоритм выполняет итерацию по коэффициентам, порядок переменных влияет на выбранный путь. В зависимости от порога сходимости и максимального количества итераций это может привести к различиям в конечных значениях коэффициентов. В случае вашего примера попробуйте изменить

fit <- cv.glmnet(x = x, y = y, family = "gaussian", alpha = alpha, 
                 lambda = lambda, 
                 foldid = foldid)

to e.g.

fit <- cv.glmnet(x = x, y = y, family = "gaussian", alpha = alpha, 
                 lambda = lambda, 
                 foldid = foldid, standardize=TRUE, thresh=1e-20, maxit=10^6)

и сделайте то же самое для своего fit2. Это может занять минуту или около того, но вы обнаружите, что различия становятся пренебрежимо малыми:

> summary(coef2 - coef1)
       1             
 Min.   :-2.038e-08  
 1st Qu.: 0.000e+00  
 Median : 0.000e+00  
 Mean   : 1.050e-10  
 3rd Qu.: 0.000e+00  
 Max.   : 3.028e-08  
> 
> min(fit$cvm)
[1] 4598.242
> 
> min(fit2$cvm)
[1] 4598.242
> 
> summary(cbind(1,x) %*% coef2 - cbind(1, x) %*% coef1)
       1             
 Min.   :-5.175e-08  
 1st Qu.:-1.457e-08  
 Median :-2.959e-10  
 Mean   : 0.000e+00  
 3rd Qu.: 1.503e-08  
 Max.   : 5.555e-08  
person Wouter    schedule 23.02.2018

Я считаю, что это связано с тем, что в glmnet используется координатный спуск, где переменные перебираются, чтобы минимизировать функцию потерь. Порядок переменных в этом случае изменит порядок итерации, что изменит пройденный путь, чтобы минимизировать функцию потерь.

person Suspicious_Gardener    schedule 22.02.2018