Como forçar pesos a não serem negativos na regressão linear

27

Estou usando uma regressão linear padrão usando o scikit-learn em python. No entanto, gostaria de forçar os pesos a serem positivos para todos os recursos (não negativos). Existe alguma maneira de conseguir isso? Eu estava procurando na documentação, mas não consegui encontrar uma maneira de fazer isso. Entendo que talvez não obtenha a melhor solução, mas preciso que os pesos sejam não negativos.

do utilizador
fonte

Respostas:

27

O que você está procurando é a regressão de mínimos quadrados não-negativa . É um problema simples de otimização na programação quadrática, onde sua restrição é que todos os coeficientes (também conhecidos como pesos) sejam positivos.

Dito isto, não há implementação padrão de mínimos quadrados não negativos no Scikit-Learn. A solicitação de recebimento ainda está aberta .

Mas, parece que o Scipy implementou o mesmo .

PS: Eu não tentei a versão scipy. Eu o encontrei apenas pesquisando no Google.

Dawny33
fonte
11
e quanto à regressão de cume onde forçou a positivo?
Charlie Parker
15

Uso uma solução alternativa com Lasso no Scikit Learn (definitivamente não é a melhor maneira de fazer as coisas, mas funciona bem). Lasso tem um parâmetro positiveque pode ser definido Truee forçar os coeficientes a serem positivos. Além disso, definir o coeficiente de Regularização alphapara ficar próximo de 0 faz com que o Lasso imite a Regressão Linear sem regularização. Aqui está o código:

from sklearn.linear_model import Lasso
lin = Lasso(alpha=0.0001,precompute=True,max_iter=1000,
            positive=True, random_state=9999, selection='random')
lin.fit(X,y)
Adarsh ​​Chavakula
fonte
0

Aqui está um exemplo de por que você desejaria fazê-lo (e aproximadamente como).

Eu tenho três modelos preditivos de preços da habitação: linear, aumento de gradiente, rede neural.

Quero misturá-los em uma média ponderada e encontrar os melhores pesos.

Executo regressão linear e obtenho uma solução com pesos como -3,1, 2,5, 1,5 e alguns interceptos.

Então, o que eu faço usando o sklearn é

blendlasso = LassoCV(alphas=np.logspace(-6, -3, 7),
                     max_iter=100000,
                     cv=5,
                     fit_intercept=False,
                     positive=True)

E recebo pesos positivos que somam (muito perto) a 1. No meu exemplo, quero o alfa que funciona melhor fora da amostra, para usar o LassoCV com validação cruzada.

Os documentos do sklearn afirmam que você não deve definir alfa como 0 por razões numéricas; no entanto, você também pode usar Lasso () direto e definir o parâmetro alfa o mais baixo possível para obter uma resposta razoável.

Rocky McNuts
fonte