Analogamente a um conjunto de ferramentas especializadas, a Regressão Lasso oferece diversas implementações para diferentes cenários. Ademais, conforme documentado no scikit-learn, estas variações atendem a necessidades específicas de seleção de parâmetros e validação.
1.1.3. Lasso
Primordialmente, o Lasso implementa a regressão linear com regularização L1. Certamente, sua formulação matemática busca minimizar a função objetivo:
\(\min_{w} \frac{1}{2n} ||X w – y||_2^2 + \alpha ||w||_1\)Similarmente a um filtro de precisão, o Lasso é capaz de produzir modelos esparsos através da eliminação seletiva de coeficientes.
1.1.3.1. Definindo o parâmetro de regularização
O parâmetro alpha controla o grau de esparsidade dos coeficientes estimados. Contudo, a seleção adequada deste parâmetro é crucial para o desempenho do modelo.
1.1.3.1.1. Uso de validação cruzada
O scikit-learn fornece LassoCV, que automaticamente seleciona o melhor alpha através de validação cruzada. Decerto, esta abordagem é preferível na prática, pois evita a seleção manual e potencialmente subótima do parâmetro.
1.1.3.1.2. Critérios de informação
Alternativamente, LassoLarsIC utiliza critérios de informação como Akaike (AIC) ou Bayesiano (BIC) para selecionar o modelo ótimo. Embora computacionalmente mais eficiente, esta abordagem requer cuidados adicionais.
1.1.3.1.3. Comparação com o modelo de mínimos quadrados
Comparado aos Mínimos Quadrados Ordinários, o Lasso oferece melhor generalização em troca de um viés introduzido. Todavia, este trade-off é frequentemente vantajoso em datasets com muitas features.
Exemplo Prático com Diferentes Abordagens
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 |
import numpy as np import matplotlib.pyplot as plt from sklearn.linear_model import Lasso, LassoCV, LassoLarsIC from sklearn.datasets import make_regression from sklearn.model_selection import train_test_split from sklearn.metrics import mean_squared_error, r2_score print("=" * 60) print("COMPARAÇÃO: DIFERENTES ABORDAGENS LASSO") print("=" * 60) # Gerar dados com features redundantes X, y = make_regression(n_samples=200, n_features=15, n_informative=5, noise=0.5, random_state=42, coef=True) # Dividir em treino e teste X_train, X_test, y_train, y_test = train_test_split( X, y, test_size=0.3, random_state=42 ) print(f"Dataset: {X.shape[0]} amostras, {X.shape[1]} features") print(f"Features informativas verdadeiras: 5") print(f"Treino: {X_train.shape[0]} amostras | Teste: {X_test.shape[0]} amostras") # 1. LASSO com alpha fixo print("\n" + "=" * 50) print("1. LASSO COM ALPHA FIXO") print("=" * 50) lasso_fixo = Lasso(alpha=0.1, max_iter=10000, random_state=42) lasso_fixo.fit(X_train, y_train) y_pred_fixo = lasso_fixo.predict(X_test) mse_fixo = mean_squared_error(y_test, y_pred_fixo) r2_fixo = r2_score(y_test, y_pred_fixo) print(f"Alpha: 0.1") print(f"Features selecionadas: {np.sum(lasso_fixo.coef_ != 0)}/15") print(f"MSE teste: {mse_fixo:.4f}") print(f"R² teste: {r2_fixo:.4f}") # 2. LASSO com validação cruzada (LassoCV) print("\n" + "=" * 50) print("2. LASSO COM VALIDAÇÃO CRUZADA (LassoCV)") print("=" * 50) # Definir range de alphas para busca alphas = np.logspace(-4, 0, 50) lasso_cv = LassoCV(alphas=alphas, cv=5, max_iter=10000, random_state=42) lasso_cv.fit(X_train, y_train) y_pred_cv = lasso_cv.predict(X_test) mse_cv = mean_squared_error(y_test, y_pred_cv) r2_cv = r2_score(y_test, y_pred_cv) print(f"Melhor alpha (CV): {lasso_cv.alpha_:.6f}") print(f"Features selecionadas: {np.sum(lasso_cv.coef_ != 0)}/15") print(f"MSE teste: {mse_cv:.4f}") print(f"R² teste: {r2_cv:.4f}") # 3. LASSO com critério de informação (LassoLarsIC) print("\n" + "=" * 50) print("3. LASSO COM CRITÉRIO DE INFORMAÇÃO (LassoLarsIC)") print("=" * 50) # AIC (Akaike Information Criterion) lasso_aic = LassoLarsIC(criterion='aic') lasso_aic.fit(X_train, y_train) y_pred_aic = lasso_aic.predict(X_test) mse_aic = mean_squared_error(y_test, y_pred_aic) r2_aic = r2_score(y_test, y_pred_aic) print(f"Alpha (AIC): {lasso_aic.alpha_:.6f}") print(f"Features selecionadas: {np.sum(lasso_aic.coef_ != 0)}/15") print(f"MSE teste: {mse_aic:.4f}") print(f"R² teste: {r2_aic:.4f}") # BIC (Bayesian Information Criterion) lasso_bic = LassoLarsIC(criterion='bic') lasso_bic.fit(X_train, y_train) y_pred_bic = lasso_bic.predict(X_test) mse_bic = mean_squared_error(y_test, y_pred_bic) r2_bic = r2_score(y_test, y_pred_bic) print(f"\nAlpha (BIC): {lasso_bic.alpha_:.6f}") print(f"Features selecionadas: {np.sum(lasso_bic.coef_ != 0)}/15") print(f"MSE teste: {mse_bic:.4f}") print(f"R² teste: {r2_bic:.4f}") # Visualização comparativa plt.figure(figsize=(15, 10)) # Gráfico 1: Comparação de coeficientes plt.subplot(2, 2, 1) modelos = [lasso_fixo, lasso_cv, lasso_aic, lasso_bic] nomes = ['Alpha Fixo', 'CV', 'AIC', 'BIC'] cores = ['red', 'blue', 'green', 'orange'] for i, modelo in enumerate(modelos): plt.bar(np.arange(15) + i*0.2, modelo.coef_, width=0.2, label=nomes[i], alpha=0.7, color=cores[i]) plt.xlabel('Features') plt.ylabel('Valor do Coeficiente') plt.title('Comparação dos Coeficientes entre Abordagens') plt.xticks(np.arange(15) + 0.3, [f'F{i+1}' for i in range(15)]) plt.legend() plt.grid(True, alpha=0.3) # Gráfico 2: Número de features selecionadas plt.subplot(2, 2, 2) features_selecionadas = [np.sum(m.coef_ != 0) for m in modelos] plt.bar(nomes, features_selecionadas, color=cores, alpha=0.7) plt.ylabel('Número de Features Selecionadas') plt.title('Esparsidade: Features Não Nulas') for i, v in enumerate(features_selecionadas): plt.text(i, v + 0.1, str(v), ha='center', va='bottom') plt.grid(True, alpha=0.3) # Gráfico 3: Performance (MSE) plt.subplot(2, 2, 3) mse_valores = [mse_fixo, mse_cv, mse_aic, mse_bic] plt.bar(nomes, mse_valores, color=cores, alpha=0.7) plt.ylabel('Mean Squared Error (Teste)') plt.title('Comparação de Performance - MSE') for i, v in enumerate(mse_valores): plt.text(i, v + 0.01, f'{v:.3f}', ha='center', va='bottom') plt.grid(True, alpha=0.3) # Gráfico 4: Performance (R²) plt.subplot(2, 2, 4) r2_valores = [r2_fixo, r2_cv, r2_aic, r2_bic] plt.bar(nomes, r2_valores, color=cores, alpha=0.7) plt.ylabel('R² Score (Teste)') plt.title('Comparação de Performance - R²') for i, v in enumerate(r2_valores): plt.text(i, v + 0.01, f'{v:.3f}', ha='center', va='bottom') plt.grid(True, alpha=0.3) plt.tight_layout() plt.show() # 💡 ANÁLISE COMPARATIVA DETALHADA print("\n" + "=" * 50) print("ANÁLISE COMPARATIVA DAS ABORDAGENS") print("=" * 50) print(f"\nRESUMO DE PERFORMANCE:") print(f"{'Método':<12} {'Alpha':<10} {'Features':<10} {'MSE':<8} {'R²':<6}") print("-" * 50) for i, (nome, modelo, mse, r2) in enumerate(zip(nomes, modelos, mse_valores, r2_valores)): features = np.sum(modelo.coef_ != 0) alpha = getattr(modelo, 'alpha_', 0.1) # Para Lasso com alpha fixo print(f"{nome:<12} {alpha:<10.6f} {features:<10} {mse:<8.4f} {r2:<6.4f}") print(f"\n💡 RECOMENDAÇÕES PRÁTICAS:") print("1. LassoCV: Ideal para maioria dos casos - seleção automática robusta") print("2. LassoLarsIC: Mais rápido, útil para datasets muito grandes") print("3. Alpha fixo: Apenas quando há conhecimento prévio do domínio") print("4. BIC tende a selecionar modelos mais esparsos que AIC") |
Interpretação dos Resultados
Inegavelmente, as diferentes abordagens produzem resultados distintos em termos de seleção de features e performance preditiva. Afinal, cada método possui suas próprias suposições e critérios de otimização.
Vantagens de Cada Abordagem
- LassoCV: Seleção robusta através de validação cruzada
- LassoLarsIC: Eficiência computacional e fundamentação estatística
- Lasso com alpha fixo: Controle direto sobre a esparsidade
Considerações de Implementação
Embora todas as abordagens implementem a mesma formulação matemática básica, suas estratégias de seleção de parâmetros diferem significativamente. Ocasionalmente, pode ser necessário testar múltiplas abordagens para encontrar a mais adequada ao problema específico.
Contudo, na prática, LassoCV é frequentemente a escolha mais segura e recomendada, pois combina robustez estatística com performance prática.
Conclusão
Portanto, o scikit-learn oferece um conjunto abrangente de implementações Lasso para diferentes necessidades. Analogamente a um kit de ferramentas especializadas, cada variação atende a cenários específicos de aplicação.
Enfim, a compreensão das diferenças entre estas implementações permite selecionar a abordagem mais adequada para cada problema, otimizando tanto a performance preditiva quanto a interpretabilidade do modelo.