Validação Cruzada — Machine Learning

João Cláudio Nunes Carvalho
6 min readAug 24, 2024

--

Vamos supor que estamos trabalhando em um modelo de machine learning supervisionado.

machine learning supervisionado: é um tipo de aprendizado de máquina onde um modelo é treinado usando um conjunto de dados rotulados. Isso significa que cada entrada no conjunto de treinamento vem com uma saída ou rótulo correspondente, que o modelo deve aprender a prever.

Voltando aqui para o que estamos falando:

Estamos então utilizando a validação cruzada para determinar um conjunto ideal de hiperparâmetros.

Essencialmente, cada conjunto de hiperparâmetros corresponde a um determinado desempenho na validação cruzada.

Após obter os melhores hiperparâmetros, precisamos finalizar um modelo (digamos, para produção); caso contrário, qual seria o propósito de todo esse trabalho?

Após obter os hiperparâmetros ideais, o que você estaria mais inclinado a fazer:

Opção 1) Treinar novamente o modelo em todos os dados (treino + validação + teste) com os hiperparâmetros ideais.

  • Observe que, se fizermos isso, não poderemos validar este novo modelo de forma confiável, pois não haverá mais dados não vistos.

Opção 2) Simplesmente seguir com o modelo de melhor desempenho com base na performance da validação cruzada.

  • Observe que, se fizermos isso, estaremos deixando de fora dados importantes que poderíamos ter usado para treinar nosso modelo.

O que você faria?

Lidar com dados desbalanceados é um desafio que todos que trabalham com aprendizado de máquina enfrentam em algum momento. Podemos tentar resolver isso diminuindo a quantidade de exemplos da classe com mais amostras ou aumentando artificialmente a quantidade de exemplos da classe com menos amostras. Cada uma dessas técnicas tem seus pontos fortes e fracos, e a escolha certa depende muito do problema.

Por que a Opção 1 é geralmente preferida?

  • Maximiza o uso dos dados: Ao treinar o modelo final com todos os dados que estão disponíveis, você garante que este modelo tenha a oportunidade de aprender com a máxima quantidade possível de informações. Isso pode nos levar a um modelo muito mais preciso.
  • Validação final: Embora não seja possível fazer uma verificação normal após treinar novamente o modelo em todos os dados, você ainda pode fazer uma verificação final usando técnicas como.

Quando considerar a Opção 2?

  • Restrições de recursos: Se você tiver pouco tempo ou capacidade de computador, pode ser demais treinar o modelo em tudo.
  • Cenários de baixa aposta: se uma pequena mudança de modelo não prejudicar muito, a Opção 2 pode ser adequada.

Considerações adicionais:

  • Documente tudo: Independentemente da opção escolhida, documente cuidadosamente todo o processo, incluindo os hiperparâmetros finais, as métricas de desempenho e qualquer avaliação final realizada.
  • Esteja preparado para iterar: O desenvolvimento de modelos de aprendizado de máquina é um processo iterativo. Esteja preparado para revisitar e ajustar seu modelo à medida que novos dados se tornam disponíveis ou os requisitos do projeto mudam.

Exemplo Prático: Previsão de Preços de Imóveis

Imagine agora que você está construindo um modelo para prever os preços de imóveis com base em algumas características como área, número de quartos, localização, etc. Você tem um conjunto de dados com informações sobre uma quantidade enorme de imóveis.

Passo 1: Validação Cruzada

Você divide seus dados em conjuntos de treinamento e validação e realiza uma validação cruzada k-fold (por exemplo, 5-fold) para testar diferentes combinações de hiperparâmetros (como a taxa de aprendizado, o número de camadas em uma rede neural, etc.). Para cada configuração de hiperparâmetros, você treina o modelo nos dados de treinamento e avalia seu desempenho nos dados de validação.

Passo 2: Escolha dos Melhores Hiperparâmetros

Após a validação cruzada, você identifica a configuração de hiperparâmetros que resultou no melhor desempenho médio nos conjuntos de validação.

Passo 3: Retreinar o Modelo (Opção 1)

Agora, você combina todos os seus dados (treinamento + validação) e treina um novo modelo usando os melhores hiperparâmetros encontrados na etapa anterior. Este modelo final é o que você implantará em produção para fazer previsões sobre novos imóveis.

Embora você não possa realizar uma validação cruzada tradicional neste modelo final, você pode:

  • Reservar um conjunto de teste: Se você tiver dados adicionais que não foram usados em nenhum estágio anterior, pode usá-los como um conjunto de teste final para avaliar o desempenho do modelo em dados completamente novos.
  • Monitorar o desempenho em produção: Após implantar o modelo, monitore seu desempenho em novas previsões de preços de imóveis. Se o desempenho se desviar significativamente das métricas de validação cruzada, pode ser necessário revisitar o modelo ou coletar mais dados.

Comparação com a Opção 2

Se você tivesse escolhido a Opção 2, teria selecionado o melhor modelo diretamente da validação cruzada e o implantado em produção. No entanto, esse modelo não teria se beneficiado do aprendizado com todos os dados disponíveis, potencialmente resultando em um desempenho ligeiramente inferior em comparação com o modelo retreinado na Opção 1.

Vamos utilizar aqui como exemplo o conjunto de dados “House Prices: Advanced Regression Techniques” disponível no Kaggle:

https://www.kaggle.com/competitions/house-prices-advanced-regression-techniques/data

Este conjunto de dados contém informações sobre diversos atributos de casas, como área, número de quartos, qualidade dos materiais, etc., juntamente com seus respectivos preços de venda. É um conjunto de dados popular para praticar técnicas de regressão e aprendizado de máquina.

Passo a Passo de uso com Python e Scikit-learn

1. Importar bibliotecas:

Importamos as bibliotecas necessárias para manipulação de dados (pandas), divisão dos dados em conjuntos de treino e teste (train_test_split), validação cruzada (KFold, cross_val_score), o algoritmo de aprendizado de máquina que usaremos (RandomForestRegressor) e a métrica de avaliação (mean_squared_error).

import pandas as pd from sklearn.model_selection 
import train_test_split, KFold, cross_val_score from sklearn.ensemble
import RandomForestRegressor from sklearn.metrics
import mean_squared_error

2. Carregar e Pré-processar os Dados:

Carregamos aqui o conjunto de dados “train.csv” em um DataFrame do Pandas. Removemos linhas com valores ausentes. Separamos os dados em features (X) e o alvo que queremos prever (y), que neste caso é o preço de venda (“SalePrice”).

data = pd.read_csv("train.csv") 
data.dropna(inplace=True)
X = data.drop("SalePrice", axis=1)
y = data["SalePrice"]

3. Dividir os Dados em Treino e Teste:

Dividimos os dados em conjuntos de treino (80%) e teste (20%). O conjunto de teste será usado apenas na avaliação final do modelo, após a validação cruzada e o ajuste dos hiperparâmetros.

X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.2, random_state=42)

4. Definir o Modelo e a Validação Cruzada:

Criamos uma instância do modelo RandomForestRegressor (você pode usar outros algoritmos).

Definimos a validação cruzada KFold com 5 folds. O parâmetro shuffle=True embaralha os dados antes de dividi-los em folds, o que ajuda a evitar vieses na avaliação.

model = RandomForestRegressor() 
kfold = KFold(n_splits=5, shuffle=True, random_state=42)

5. Realizar a Validação Cruzada:

Usamos a função cross_val_score para realizar a validação cruzada. O modelo é treinado e avaliado 5 vezes (uma para cada fold). A métrica de avaliação é o erro quadrático médio negativo (neg_mean_squared_error), que é usado pois a função cross_val_score maximiza as pontuações por padrão. Convertemos as pontuações negativas em positivas para facilitar a interpretação.

scores = cross_val_score(model, X_train, y_train, cv=kfold, scoring='neg_mean_squared_error') 
mse_scores = -scores print("MSE em cada Fold:", mse_scores) 
print("MSE Médio:", mse_scores.mean())

6. Otimizar Hiperparâmetros (Opcional):

Definimos uma grade de hiperparâmetros para testar (número de árvores e profundidade máxima da árvore).Usamos GridSearchCV para realizar a busca em grade, combinando a validação cruzada com a otimização de hiperparâmetros.

O melhor conjunto de hiperparâmetros é armazenado em best_params.

param_grid = {'n_estimators': [50, 100, 200], 'max_depth': [None, 10, 20]} grid_search = GridSearchCV(estimator=model, param_grid=param_grid, cv=kfold, scoring='neg_mean_squared_error') 
grid_search.fit(X_train, y_train)
best_params = grid_search.best_params_

7. Retreinar o Modelo Final:

Criamos um novo modelo com os melhores hiperparâmetros encontrados. Treinamos esse modelo final em todos os dados de treinamento (combinando os conjuntos de treino e validação usados na validação cruzada).

final_model = RandomForestRegressor(**best_params) 
final_model.fit(X_train, y_train)

8. Avaliar o Modelo Final:

Fazemos previsões no conjunto de teste (que não foi usado em nenhum momento anterior). Calculamos o erro quadrático médio (MSE) para avaliar o desempenho do modelo em dados novos.

y_pred = final_model.predict(X_test) 
mse = mean_squared_error(y_test, y_pred)
print("Erro quadrático médio no conjunto de teste:", mse)

A validação cruzada é uma ferramenta poderosa para construir modelos de aprendizado de máquina mais robustos e confiáveis. Ao incorporar essa técnica em seu fluxo de trabalho, você estará melhor preparado para evitar o overfitting e garantir que seus modelos generalizem bem para novos dados.

--

--

João Cláudio Nunes Carvalho
João Cláudio Nunes Carvalho

Written by João Cláudio Nunes Carvalho

Professor of Physics at the Federal Institute of Ceará. Phd in physics(UFC). MBA in Data Science and Analytics — USP — University of São Paulo

No responses yet