
Já sabemos que a resolução de um problema de classificação utilizando o algoritmo Naive Bayes consistem em determinar a máxima probabilidade a posteriori, dada por:
A depender da natureza dos recursos de X, pode-se assumir que estes sigam determinada distribuição de probabilidade. Quando se trata de dados contínuos, na maioria das vezes, assume-se que estes seguem uma distribuição de probabilidade Gaussiana. Nesse caso, as probabilidades na parcela do somatório na Equação 1, pode ser obtida pela Equação 2 abaixo:
E, desse modo, os únicos parâmetros que precisamos estimar, a partir dos dados de treinamento, são a média (μ) e o desvio padrão (σ) de cada classe.
Simples, né?
Vejamos isto em uma aplicação prática.
Um problema clássico de classificação em Machine Learning é o encontrado no banco de dados Iris.
O conjunto de dados é composto por medidas do comprimento e largura (em centímetros) das sépalas e pétalas de diversas flores Íris.
São também previamente identificadas espécies do tipo Iris-setosa, Iris-setosa, Iris-versicolor e Iris-virginica de acordo com as medidas de comprimento e larguras de suas sépalas e pétalas.
Nosso objetivo é criar um modelo de machine learning supervisionado que aprenderá com o conjunto de dados e posteriormente será capaz de classificar uma flor Íris em algumas das espécies mencionadas anteriormente com base nas medidas de comprimento e larguras de suas sépalas e pétalas.
Para tanto, utilizaremos o modelo Naive Bayes Gaussiano. Maiores detalhes sobre o algoritmo Naive Bayes você encontra aqui.
OBS: O notebook desta aplicação, com todos os códigos mostrados aqui está disponível no Github.
Vamos então colocar a mão na massa e construir nosso modelo!
O primeiro passo na construção do nosso modelo é importar as bibliotecas básicas.
Em seguida carregamos o conjunto de dados em um dataframe pandas.
O primeiro comando, acima, carrega e guarda o conjunto de dados na forma de um dataframe pandas em iris_dataset. O segundo exibe as dimensões desse conjunto de dados e o terceiro mostra as 5 primeiras linhas do dataframe.
As dimensões do conjunto de dados são 150×5. Isso significa que temos 150 exemplos de flores Íris, com suas respectivas medidas de comprimento e larguras das sépalas e pétalas (4 recursos) e suas classificações correspondentes.
Vamos checar as classes presentes no conjunto de dados.
Como esperado, temos três classes diferentes: Iris-setosa, Iris-versicolor, Iris-virginica.
O comando a seguir nos dá uma descrição estatística geral do nosso conjunto de dados.
É importante verificar se não há dados ausentes no conjunto de dados. Na linha ‘count’ podemos observar que todos os recursos possuem 150 pontos. O que indica que não há dados ausentes.
Podemos confirmar isso através do comando abaixo, que nos dará a quantidade de dados ausentes no conjunto de dados.
Vamos analisar o comportamento gráfico dos recursos do nosso banco de dados.
O comando abaixo mostrará os gráficos cruzados entre todos os recursos do banco de dados e separará por cores as diferentes espécies de Íris.
Nota-se uma clara separação entre as classes, principalmente para a espécie Íris-Setosa. Como vamos aplicar o algorítimo GNB, é importante atentar para as distribuições de probabilidade dos recursos. Quanto mais próximas de uma distribuição Gaussiana, espera-se que melhor seja o desempenho do modelo.
Temos agora que definir quem serão os recursos do nosso modelo, ou seja, aqueles que serão usados pelo modelo para prever as classes, as quais constituem o o alvo do modelo. Como já foi mencionado, os recursos do nosso modelo serão as medidas de comprimento e largura das sépalas e pétalas, ou seja, todos os recursos são numéricos. Já o alvo é o tipo de espécie de flor Íris que, como já vimos, são três possíveis: Iris-setosa, Iris-versicolor, Iris-Virginia.
Guardaremos os recursos na variável X, que será uma matriz 150×4 e o alvo em y, um vetor de comprimento 150.
Definidos os recursos e alvo, precisamos separar os dados em dados de treinamento e teste. Os dados de treinamento serão usados para ensinar o modelo. Já os dados de teste serão usados para mensurar o seu desempenho, ou, sua capacidade de generalização de previsão.
O comando abaixo separa os dados em dados de treinamento, composto por 75% do total de dados, e dados de teste, formado pelos 25% restantes, no qual o modelo será avaliado.
Vamos checar as dimensões dos dados de treinamento e de teste.
Portanto, o modelo será treinado com 112 exemplos de flores Íris, e terá seu desempenho testado na classificação de 38 novos exemplos.
Primeiro, implementaremos o algoritmo Naive Bayes Gaussiano diretamente em python, do zero. Em seguida, usaremos as bibliotecas do sklearn para criar um modelo GNB e compararemos os resultados.
Seguindo as definições do algoritmo NB, primeiramente vamos criar uma função que calcula as probabilidades a priori de cada classe.
Em seguida, calculamos as médias e desvios padrões de cada uma das classes.
Com as médias e os desvios padrões calculados anteriormente, podemos gerar a fdp gaussiana de cada classe.
E, por fim, usamos o conceito de máxima probabilidade a posteriori para prever a classe de flor Íris, com base no modelo GNB.
Aplicamos agora as funções definidas acima aos dados de flores Íris.
Primeiro as probabilidades a priori.
Depois as médias e desvios Padrões.
E, finalmente, a previsão para os 38 exemplos de teste.
O exercício de se criar um modelo do zero é interessante para fins didáticos. No entanto, na maioria das aplicações práticas de ML utilizamos bibliotecas previamente construídas para este fim.
Neste exemplo utilizaremos a biblioteca sklearn para construir um modelo GNB.
Começamos por importar a biblioteca.
A sequência de comandos abaixo criar um modelo GNB, depois o treina com os dados de treinamento e, em seguida, faz a previsão para os dados de teste.
Agora que já treinamos os modelos e efetuamos as classificações de flores íris nos dados de teste, precisamos saber o quão bom foi o desempenho de cada modelo.
Dentro da biblioteca sklearn há um módulo de avaliação de modelos. Vamos importa-lo.
Primeiro, vejamos o desempenho do nosso modelo criado do zero.
O desempenho do modelo criado a partir do Sklearn é mostrado abaixo.
Vemos que em ambos os casos, a acurácia foi de 100%, assim como nas métricas de precisão (precision), revocação(recall) e f1-score.
As matrizes de confusão abaixo reforçam o ótimo desempenho dos modelos, as quais apresentam somente valores de na diagonal principal, como é o ideal.
As métricas dos dois modelos são exatamente iguais. Ambos os modelos conseguem prever com exatidão todas as espécies de Íris dos dados de teste.
Para mais detalhes sobre as métricas de classificação clique aqui.
Todos os códigos mostrados nesse artigo estão disponíveis no Github.