1
resposta

[Projeto] avaliando nossas métricas

import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
import joblib
import matplotlib.cm as cm

from sklearn.preprocessing import OneHotEncoder
from sklearn.cluster import KMeans
from sklearn.metrics import silhouette_score, silhouette_samples

# 1. Carregar dados
url = 'https://raw.githubusercontent.com/alura-cursos/Clusterizacao-dados-sem-rotulo/main/Dados/dados_mkt.csv'
df = pd.read_csv(url)

# 2. One-Hot Encoding da coluna sexo
encoder = OneHotEncoder(categories=[['F', 'M', 'NE']], sparse_output=False)
sexo_cod = encoder.fit_transform(df[['sexo']])
sexo_df = pd.DataFrame(sexo_cod, columns=encoder.get_feature_names_out(['sexo']))
dados = pd.concat([df, sexo_df], axis=1).drop('sexo', axis=1)

# 3. Salvar encoder
joblib.dump(encoder, 'encoder.pkl')

# 4. Treinar modelo inicial
mod_kmeans = KMeans(n_clusters=2, random_state=45, n_init='auto')
mod_kmeans.fit(dados)

# 5. Métricas iniciais
print("Inércia:", mod_kmeans.inertia_)
print("Silhouette:", silhouette_score(dados, mod_kmeans.predict(dados)))

# 6. Avaliar vários k
def avaliacao(dados):
    inercia, silhueta = [], []
    for k in range(2, 21):
        modelo = KMeans(n_clusters=k, random_state=45, n_init='auto')
        pred = modelo.fit_predict(dados)
        inercia.append(modelo.inertia_)
        silhueta.append(silhouette_score(dados, pred))
    return silhueta, inercia

silhueta, inercia = avaliacao(dados)

for k, s in enumerate(silhueta, start=2):
    print(f'k={k} - silhueta={s:.4f}')

# 7. Gráfico de silhueta
def graf_silhueta(n_clusters, dados):
    modelo = KMeans(n_clusters=n_clusters, random_state=45, n_init='auto')
    pred = modelo.fit_predict(dados)
    media = silhouette_score(dados, pred)
    amostras = silhouette_samples(dados, pred)

    fig, ax = plt.subplots(figsize=(9, 7))
    ax.set_xlim([-0.1, 1])
    ax.set_ylim([0, len(dados) + (n_clusters + 1) * 10])

    y_lower = 10
    for i in range(n_clusters):
        vals = amostras[pred == i]
        vals.sort()
        tam = vals.shape[0]
        y_upper = y_lower + tam
        cor = cm.nipy_spectral(float(i) / n_clusters)
        ax.fill_betweenx(np.arange(y_lower, y_upper), 0, vals,
                         facecolor=cor, edgecolor=cor, alpha=0.7)
        ax.text(-0.05, y_lower + 0.5 * tam, str(i))
        y_lower = y_upper + 10

    ax.axvline(x=media, color='red', linestyle='--')
    ax.set_title(f'Silhueta para {n_clusters} clusters')
    ax.set_xlabel('Coeficiente de silhueta')
    ax.set_ylabel('Cluster')
    ax.set_yticks([])
    plt.show()

graf_silhueta(2, dados)

# 8. Método do cotovelo
def plot_cotovelo(inercia):
    plt.figure(figsize=(8, 4))
    plt.plot(range(2, 21), inercia, 'bo-')
    plt.xlabel('Número de clusters')
    plt.ylabel('Inércia')
    plt.title('Método do Cotovelo')
    plt.show()

plot_cotovelo(inercia)
1 resposta

Olá, Moacir! Como vai?

Parabéns pela resolução da atividade!

Observei que você explorou o uso do silhouette score para avaliar a qualidade dos agrupamentos com Python, utilizou muito bem o método do cotovelo para analisar a quantidade ideal de clusters e ainda compreendeu a importância da visualização gráfica para interpretar os resultados de forma clara e prática.

Continue postando as suas soluções, com certeza isso ajudará outros estudantes e tem grande relevância para o fórum.

Sugestão de conteúdo para você mergulhar ainda mais no tema:

Alguns materiais estão em inglês, mas é possível compreendê-los usando o recurso de tradução de páginas do próprio navegador.

Fico à disposição! E se precisar, conte sempre com o apoio do fórum.

Abraço e bons estudos!

AluraConte com o apoio da comunidade Alura na sua jornada. Abraços e bons estudos!