Aprenda a criar um Diagrama de Pareto utilizando Matplotlib no Python! Esse diagrama é uma ferramenta de qualidade importante adotada por diversas empresas.
Caso prefira esse conteúdo no formato de vídeo-aula, assista ao vídeo abaixo ou acesse o nosso canal do YouTube!
Para receber por e-mail o(s) arquivo(s) utilizados na aula, preencha:
Criando Diagrama de Pareto com Matplotlib
Na aula de hoje eu vou te ensinar como construir Diagrama de Pareto com Matplotlib. O Matplotlib é um dos pacotes mais conhecidos em Python quando estamos lidando com construção de gráficos.
O Diagrama de Pareto é uma importante ferramenta de qualidade adotada pelas empresas, com o objetivo de investigar e identificar problemas, suas causas e possíveis soluções que podem ser tomadas.
Nesta aula, vou te mostrar duas formas de criar o Diagrama de Pareto no Matplotlib para que você possa fazer suas análises de dados de forma correta e intuitiva. O objetivo é que você compreenda a lógica do diagrama e todo o processo de criação dele.
Então, faça o download do material disponível e vem comigo, que eu vou te mostrar o passo a passo para construir e utilizar o Diagrama de Pareto com Matplotlib.
Apresentação dos Dados e dos Diagramas de Pareto
No material disponível para download, você encontrará a base de dados que utilizaremos como exemplo ao longo desta aula.
Dentro dela, temos os dados fictícios sobre uma empresa de cartão de crédito, listando os principais problemas e defeitos que ocorrem durante a produção desses cartões.
A partir desses dados, geraremos nossos Diagramas de Pareto, onde as barras representam a frequência dos problemas, e a linha representa o percentual acumulado dos erros.
Essa é a estrutura base do Diagrama de Pareto, um gráfico de colunas que exibe frequências em ordem decrescente, seguindo o Princípio de Pareto. Esse conceito afirma que aproximadamente 80% dos efeitos podem ser atribuídos a 20% das causas.
O Princípio de Pareto pode ser aplicado a diversas situações, permitindo realizar análises e estabelecer prioridades. O Diagrama de Pareto pode auxiliar na identificação de pontos de grande potencial e de problema, determinando os principais influenciadores para isso.
No contexto do nosso exemplo, ele pode ser útil para que a empresa consiga identificar e direcionar seus esforços para resolver os problemas prioritários, que correspondem à maior parte dos erros.
Exemplo da Aula – Contexto
Para a construção dos nossos Diagramas de Pareto, vamos considerar a base de dados disponível sobre os principais problemas na produção de cartões de crédito.
O objetivo da empresa fabricante de cartões é reduzir o número de erros em seus produtos. Para isso, ela coletou dados sobre os tipos de erros que ocorrem em sua linha de produção.
Os dados coletados, presentes na nossa base de dados, correspondem aos erros encontrados em uma amostra de 1000 cartões de crédito durante uma semana de produção.
A partir disso, vamos desenvolver nosso Diagrama de Pareto para identificar os tipos de erros mais frequentes e, assim, priorizar e direcionar as ações da empresa para reduzir esse número de erros.
Criando o DataFrame
Vamos começar criando o DataFrame que iremos utilizar e visualizando os dados presentes nele.
import pandas as pd
DADOS = "./dados/cartoes.csv"
df = pd.read_csv(DADOS)
df
Esses foram os erros encontrados na produção de 1000 cartões.
Ordenando os Dados
Como o Diagrama de Pareto é construído com as barras ordenadas em ordem decrescente de frequência, o primeiro passo que tomaremos será reordenar a coluna frequência do DataFrame em ordem decrescente.
Para isso, utilizaremos o método sort_values, passando como parâmetro a coluna pela qual desejamos reordenar (by=”frequencia”) e a forma de ordenação como decrescente (ascending=False).
df = df.sort_values(by="frequencia", ascending=False)
df
Calculando a Frequência Relativa e Acumulada
Agora que já ordenamos nosso DataFrame, precisamos criar novas colunas para calcular e criar o percentual acumulado do gráfico de Pareto.
Primeiro, vamos criar a coluna de frequência relativa, que calculará o percentual de cada tipo de erro em relação ao total. Para isso, vamos dividir a frequência de cada defeito pela soma total de erros.
df["frequencia_relativa"] = df["frequencia"] / df["frequencia"].sum()
df
Além disso, precisamos calcular a frequência acumulada, que representa a soma progressiva das frequências. Para esse cálculo, podemos utilizar o método cumsum.
df["frequencia_acumulada"] = df["frequencia"].cumsum()
df
E, por fim, criaremos a coluna de frequência relativa acumulada, que será a soma progressiva dos percentuais relativos.
df["frequencia_relativa_acumulada"] = df["frequencia_relativa"].cumsum()
df
Com isso, já temos os dados necessários para construir Diagrama de Pareto.
Criando um Sistema de Eixos
Para a construção do nosso gráfico, utilizaremos o sistema de eixos do Matplotlib. Então, vamos criar uma figura (fig) e um sistema de eixos (ax).
import matplotlib.pyplot as plt
fig, ax = plt.subplots()
Criando o Gráfico de Barras com Matplotlib
O próximo passo para a construção do Diagrama de Pareto será a criação do gráfico de barras. Para criar esse gráfico, precisamos passar os dados referentes ao tipo de defeito e à frequência.
import matplotlib.pyplot as plt
fig, ax = plt.subplots()
ax.bar(df["tipo_de_defeito"], df["frequencia"])
plt.show()
Perceba que ainda temos alguns problemas como sobreposição de valores, mas iremos ajustar isso depois.
Gráfico de Linhas com Matplotlib
O nosso gráfico de linhas será criado com base na coluna tipo_de_defeito e na frequencia_relativa_acumulada. Assim como nosso gráfico de barras, o eixo X do nosso gráfico de linha será o tipo de defeito apresentado.
No entanto, para visualizarmos corretamente as informações do gráfico de linha, precisamos criar um segundo sistema de eixos que compartilhe o eixo X com o gráfico de barras, mas tenha seu próprio eixo Y.
Isso é importante porque a frequência relativa acumulada está em uma unidade de medida diferente da frequência e, portanto, em escalas diferentes.
Para fazer isso, podemos utilizar o método twinx() do Matplotlib. Esse método cria um segundo sistema de eixos para o gráfico de linha, que compartilha o eixo X já existente, mas permite definirmos um eixo Y independente.
Para plotarmos o gráfico de linhas, utilizaremos o método plot, definindo as colunas tipo_de_defeito e frequencia_relativa_acumulada. Além disso, para melhorar a visualização, passaremos o parâmetro color com o valor red (vermelho).
import matplotlib.pyplot as plt
fig, ax = plt.subplots()
ax2 = ax.twinx()
ax.bar(df["tipo_de_defeito"], df["frequencia"])
ax2.plot(df["tipo_de_defeito"], df["frequencia_relativa_acumulada"], color="red")
plt.show()
Ajustando os Rótulos do Gráfico
Agora ajustaremos os rótulos nos ticks (tracinhos) presentes no eixo X do nosso gráfico, utilizando o método tick_params.
Esse método permite editar os parâmetros dos ticks nos eixos de um gráfico. Para isso, precisamos informar o eixo (axis) que será modificado e qual parâmetro queremos ajustar.
Como o objetivo é tornar os rótulos no tick do eixo X legíveis, vamos passar o parâmetro rotation (rotação) com o valor de 90.
Além disso, adicionaremos um rótulo a cada um dos eixos Y pelo método set_ylabel.
import matplotlib.pyplot as plt
fig, ax = plt.subplots()
ax2 = ax.twinx()
ax.bar(df["tipo_de_defeito"], df["frequencia"])
ax2.plot(df["tipo_de_defeito"], df["frequencia_relativa_acumulada"], color="red")
ax.tick_params(axis="x", rotation=90)
ax.set_ylabel("Frequência")
ax2.set_ylabel("Percentual")
plt.show()
A rotação adequada dos rótulos nos ticks facilita a leitura do gráfico, e você pode ajustar conforme sua preferência, colocando outros valores para o parâmetro rotation.
Formatando os Valores em Porcentagem
Perceba que nosso rótulo de Percentual não apresenta os valores como porcentagem, mas sim como números decimais. Para corrigir isso, vamos importar o módulo ticker da biblioteca do Matplotlib.
import matplotlib.ticker as mtick
Feito isso, vamos usar o método set_major_formatter, passando como argumento a classe PercentFormatter do módulo ticker e o valor de 1 para indicar que essa escala está de 0 até 1.
import matplotlib.pyplot as plt
import matplotlib.ticker as mtick
fig, ax = plt.subplots()
ax2 = ax.twinx()
ax.bar(df["tipo_de_defeito"], df["frequencia"])
ax2.plot(df["tipo_de_defeito"], df["frequencia_relativa_acumulada"], color="red")
# Rotacionando os ticks do Eixo X:
ax.tick_params(axis="x", rotation=90)
# Definindo os rótulos dos Eixos Y:
ax.set_ylabel("Frequência")
ax2.set_ylabel("Percentual")
# Formatando o Eixo Y do Gráfico de Linha como percentual:
ax2.yaxis.set_major_formatter(mtick.PercentFormatter(1))
plt.show()
Perceba que agora já temos a base do nosso gráfico de Pareto, onde conseguimos visualizar as informações de forma clara. Porém, podemos fazer alguns ajustes para melhorar o visual dele.
Melhorias Visuais no Gráfico – Estilos e Cores no Matplotlib
Um ponto muito importante no que diz respeito ao visual dos gráficos é a escolha de cores adequadas.
Como já foi demonstrado, podemos alterar as cores utilizando o parâmetro colorpar e definindo a cor desejada. No entanto, existem uma série de estilos pré-instalados no Matplotlib que podemos utilizar para mudar as cores e os estilos dos gráficos.
Você pode conferir todos os estilos disponíveis na documentação oficial do Matplotlib.
O Matplotlib cria gráficos com um estilo padrão (default), que inclui um ciclo de cores predefinido. Dentro de cada estilo, podemos acessar esse ciclo de cores utilizando os códigos C0, C1, etc.
O Matplotlib interpreta esses códigos como referências ao ciclo de cores ativo e atribui automaticamente a cor correspondente ao gráfico, facilitando a distinção de diferentes séries de dados ou elementos do gráfico.
Podemos utilizá-los para personalizar nossos gráficos e os eixos presentes neles. Vamos definir nosso gráfico de barras e o eixo Y correspondente a ele com a cor C0, e o gráfico de linhas e seu eixo Y com a cor C1.
import matplotlib.pyplot as plt
import matplotlib.ticker as mtick
fig, ax = plt.subplots()
ax2 = ax.twinx()
ax.bar(df["tipo_de_defeito"], df["frequencia"], color="C0")
ax2.plot(df["tipo_de_defeito"], df["frequencia_relativa_acumulada"], color="C1")
# Rotacionando os ticks do Eixo X:
ax.tick_params(axis="x", rotation=90)
# Coloração do eixo Y e dos ticks dele:
ax.set_ylabel("Frequência", color="C0")
ax.tick_params(axis="y", labelcolor="C0")
# Coloração do eixo Y2 e dos ticks dele:
ax2.set_ylabel("Percentual", color="C1")
ax2.tick_params(axis="y", labelcolor="C1")
# Formatando o Eixo Y do Gráfico de Linha como percentual:
ax2.yaxis.set_major_formatter(mtick.PercentFormatter(1))
plt.show()
Alinhar as cores dos elementos visuais (barras e linhas) com os eixos correspondentes facilita a interpretação e compreensão do gráfico.
Tamanho, Marcadores e Título no Gráfico
Para completar os ajustes do gráfico, podemos definir o tamanho da figura, adicionar marcadores ao longo da linha para melhorar a visualização e incluir um título claro e descritivo que represente os dados apresentados.
Para ajustar o tamanho da figura, utilizamos o parâmetro figsize no método subplots, passando os valores de largura e altura em uma tupla. Os marcadores são adicionados ao gráfico de linha através do parâmetro marker.
Por fim, para incluir um título no gráfico, utilizamos o método suptitle.
import matplotlib.pyplot as plt
import matplotlib.ticker as mtick
fig, ax = plt.subplots(figsize=(10, 6))
ax2 = ax.twinx()
ax.bar(df["tipo_de_defeito"], df["frequencia"], color="C0")
ax2.plot(df["tipo_de_defeito"], df["frequencia_relativa_acumulada"], color="C1", marker="o")
# Rotacionando os ticks do Eixo X:
ax.tick_params(axis="x", rotation=90)
# Coloração do eixo Y e dos ticks dele:
ax.set_ylabel("Frequência", color="C0")
ax.tick_params(axis="y", labelcolor="C0")
# Coloração do eixo Y2 e dos ticks dele:
ax2.set_ylabel("Percentual", color="C1")
ax2.tick_params(axis="y", labelcolor="C1")
# Formatando o Eixo Y do Gráfico de Linha como percentual:
ax2.yaxis.set_major_formatter(mtick.PercentFormatter(1))
# Definindo o Título
fig.suptitle("Frequência e percentual acumulado de tipos de defeito nos cartões de crédito")
plt.show()
Com isso, concluímos nosso primeiro gráfico do Diagrama de Pareto.
Aplicando outros Estilos ao Gráfico
Uma funcionalidade interessante do Matplotlib é a possibilidade de alterar rapidamente o visual do gráfico apenas alterando o estilo dele. Para isso, podemos usar a função use do método style, passando o estilo desejado.
import matplotlib.pyplot as plt
import matplotlib.ticker as mtick
# estilo bmh
plt.style.use("bmh")
fig, ax = plt.subplots(figsize=(10, 6))
ax2 = ax.twinx()
ax.bar(df["tipo_de_defeito"], df["frequencia"], color="C0")
ax2.plot(df["tipo_de_defeito"], df["frequencia_relativa_acumulada"], color="C1", marker="o")
# Rotacionando os ticks do Eixo X:
ax.tick_params(axis="x", rotation=90)
# Coloração do eixo Y e dos ticks dele:
ax.set_ylabel("Frequência", color="C0")
ax.tick_params(axis="y", labelcolor="C0")
# Coloração do eixo Y2 e dos ticks dele:
ax2.set_ylabel("Percentual", color="C1")
ax2.tick_params(axis="y", labelcolor="C1")
# Formatando o Eixo Y do Gráfico de Linha como percentual:
ax2.yaxis.set_major_formatter(mtick.PercentFormatter(1))
# Definindo o Título
fig.suptitle("Frequência e percentual acumulado de tipos de defeito nos cartões de crédito")
plt.show()
Perceba que com uma única linha de código foi possível alterar toda a aparência do gráfico. Existem vários estilos pré-definidos que podemos aplicar, facilitando a criação e personalização dos gráficos.
Repare também que como utilizamos os códigos de cores C0 e C1, o Matplotlib plotou o gráfico com as cores correspondentes a esse ciclo dentro do estilo bmh.
Além disso, esse estilo adiciona linhas de grade ao nosso gráfico, que podemos remover facilmente através do método grid com o valor de False.
import matplotlib.pyplot as plt
import matplotlib.ticker as mtick
# estilo bmh
plt.style.use("bmh")
fig, ax = plt.subplots(figsize=(10, 6))
ax2 = ax.twinx()
ax.bar(df["tipo_de_defeito"], df["frequencia"], color="C0")
ax2.plot(df["tipo_de_defeito"], df["frequencia_relativa_acumulada"], color="C1", marker="o")
# Rotacionando os ticks do Eixo X:
ax.tick_params(axis="x", rotation=90)
# Coloração do eixo Y e dos ticks dele:
ax.set_ylabel("Frequência", color="C0")
ax.tick_params(axis="y", labelcolor="C0")
# Coloração do eixo Y2 e dos ticks dele:
ax2.set_ylabel("Percentual", color="C1")
ax2.tick_params(axis="y", labelcolor="C1")
# Formatando o Eixo Y do Gráfico de Linha como percentual:
ax2.yaxis.set_major_formatter(mtick.PercentFormatter(1))
# Definindo o Título
fig.suptitle("Frequência e percentual acumulado de tipos de defeito nos cartões de crédito")
# Remover linhas de grade
ax.grid(False)
ax2.grid(False)
plt.show()
Criando o Segundo Modelo do Diagrama de Pareto
O primeiro modelo que geramos do Diagrama de Pareto é uma das formas mais tradicionais de representarmos esse gráfico. Porém, pode ser interessante removermos elementos desnecessários, visando uma apresentação mais clara.
Uma das formas de fazermos isso é tirar os eixos Y e adicionar as informações presentes neles próximas aos elementos correspondentes. Utilizaremos nosso último gráfico como base e apenas faremos as modificações necessárias.
Vamos começar adicionando os valores sobre as barras usando o método bar_label(). Para definir o valor de cada rótulo, utilizamos a coleção de barras desenhadas no gráfico, acessando-a através do objeto de eixo (ax.containers[0]).
Quando plotamos nosso gráfico de barras (ax.bar()), o Matplotlib cria uma coleção de barras, cada uma representada por um artist. Essa coleção de barras é armazenada como um container de artists dentro do objeto de eixos.
Ao acessar ax.containers[0], estamos acessando essa coleção de barras, que o método bar_label() utiliza as alturas de cada uma delas para criar os rótulos.
Além disso, dentro do método bar_label, podemos passar os parâmetros color, para definir a cor, fontweight para deixar a letra em negrito (bold), e o espaçamento entre o rótulo e a barra com padding.
import matplotlib.pyplot as plt
import matplotlib.ticker as mtick
# estilo bmh
plt.style.use("bmh")
fig, ax = plt.subplots(figsize=(10, 6))
ax2 = ax.twinx()
ax.bar(df["tipo_de_defeito"], df["frequencia"], color="C0")
ax2.plot(df["tipo_de_defeito"], df["frequencia_relativa_acumulada"], color="C1", marker="o")
# Rotacionando os ticks do Eixo X:
ax.tick_params(axis="x", rotation=90)
# Coloração do eixo Y e dos ticks dele:
ax.set_ylabel("Frequência", color="C0")
ax.tick_params(axis="y", labelcolor="C0")
# Coloração do eixo Y2 e dos ticks dele:
ax2.set_ylabel("Percentual", color="C1")
ax2.tick_params(axis="y", labelcolor="C1")
# Formatando o Eixo Y do Gráfico de Linha como percentual:
ax2.yaxis.set_major_formatter(mtick.PercentFormatter(1))
# Definindo o Título
fig.suptitle("Frequência e percentual acumulado de tipos de defeito nos cartões de crédito")
# Remover linhas de grade
ax.grid(False)
ax2.grid(False)
#Valores sobre as barras usando bar_label
ax.bar_label(ax.containers[0], color="C0", fontweight="bold", padding=2)
plt.show()
Agora precisamos fazer o mesmo para as marcações no nosso gráfico de linha. Para isso, vamos construir um loop for que irá percorrer cada linha presente na coluna frequencia_relativa_acumulada.
Para obtermos o índice e o valor de cada linha da coluna, utilizaremos a função enumerate.
Dentro do loop, aplicaremos o método annotate para adicionar um rótulo com o valor formatado em percentual (f”{percentual:.0%}) para cada marca do gráfico de linha.
Para especificar as coordenadas onde o rótulo deve ser colocado, utilizaremos o i para indicar a marcação à qual se refere, e o percentual para indicar o valor naquela posição, a altura dele.
Além disso, precisamos melhorar o posicionamento desses valores utilizando os parâmetros textcoords=“offset points” e xytext=(0, 10). Esses dois parâmetros nos permitem definir as coordenadas do texto (rótulo) com relação ao ponto.
Por fim, podemos utilizar os parâmetros ha para definir o alinhamento horizontal do texto, color para definir a cor e fontweight para deixar o texto em negrito.
import matplotlib.pyplot as plt
import matplotlib.ticker as mtick
# estilo bmh
plt.style.use("bmh")
fig, ax = plt.subplots(figsize=(10, 6))
ax2 = ax.twinx()
ax.bar(df["tipo_de_defeito"], df["frequencia"], color="C0")
ax2.plot(df["tipo_de_defeito"], df["frequencia_relativa_acumulada"], color="C1", marker="o")
# Rotacionando os ticks do Eixo X:
ax.tick_params(axis="x", rotation=90)
# Coloração do eixo Y e dos ticks dele:
ax.set_ylabel("Frequência", color="C0")
ax.tick_params(axis="y", labelcolor="C0")
# Coloração do eixo Y2 e dos ticks dele:
ax2.set_ylabel("Percentual", color="C1")
ax2.tick_params(axis="y", labelcolor="C1")
# Formatando o Eixo Y do Gráfico de Linha como percentual:
ax2.yaxis.set_major_formatter(mtick.PercentFormatter(1))
# Definindo o Título
fig.suptitle("Frequência e percentual acumulado de tipos de defeito nos cartões de crédito")
# Remover linhas de grade
ax.grid(False)
ax2.grid(False)
#Valores sobre as barras usando bar_label
ax.bar_label(ax.containers[0], color="C0", fontweight="bold", padding=2)
# valores sobre a linha usando annotate
for i, percentual in enumerate(df["frequencia_relativa_acumulada"]):
ax2.annotate(f"{percentual:.0%}", (i, percentual), textcoords="offset points", xytext=(0, 10), ha="center", color="C1", fontweight="bold")
plt.show()
Feito isso, só precisamos fazer os ajustes finais no gráfico, removendo os elementos desnecessários.
Podemos começar removendo as linhas que definiam os rótulos e as cores dos eixos Y. Em seguida, utilizaremos o tick_params para ocultar as escalas e os ticks desses eixos, definindo o eixo como y e os parâmetros left e labelleft, e right e labelright como false.
Por fim, podemos remover as bordas dos nossos sistemas de eixos. Cada borda é denominada de spine, então podemos percorrer os valores das bordas de cada eixo e definir o valor de set_visible como False.
import matplotlib.pyplot as plt
# estilo bmh
plt.style.use("bmh")
fig, ax = plt.subplots(figsize=(10, 6))
ax2 = ax.twinx()
ax.bar(df["tipo_de_defeito"], df["frequencia"], color="C0")
ax2.plot(df["tipo_de_defeito"], df["frequencia_relativa_acumulada"], color="C1", marker="o")
# Rotacionando os ticks do Eixo X:
ax.tick_params(axis="x", rotation=90, size=0)
# Remover linhas de grade
ax.grid(False)
ax2.grid(False)
#Valores sobre as barras usando bar_label
ax.bar_label(ax.containers[0], color="C0", fontweight="bold", padding=2)
# valores sobre a linha usando annotate
for i, percentual in enumerate(df["frequencia_relativa_acumulada"]):
ax2.annotate(f"{percentual:.0%}", (i, percentual), textcoords="offset points", xytext=(0, 10), ha="center", color="C1", fontweight="bold")
# Retirar escalas e rótulos dos eixos y
ax.tick_params(axis="y", left=False, labelleft=False)
ax2.tick_params(axis="y", right=False, labelright=False)
# Remover borda do ax e ax2
for spine in ax.spines.values():
spine.set_visible(False)
for spine in ax2.spines.values():
spine.set_visible(False)
# Definindo o Título
fig.suptitle("Frequência e percentual acumulado de tipos de defeito nos cartões de crédito")
plt.show()
Com isso, nosso segundo Diagrama de Pareto com Matplotlib está pronto. Ainda é possível ajustar e melhorar a visualização, escolhendo cores e estilos que contrastem melhor entre si, tornando a visualização mais clara.
Conclusão – Criando Diagrama de Pareto com Matplotlib
Na aula de hoje, ensinei como construir Diagramas de Pareto com Matplotlib, uma ferramenta de qualidade adotada pelas empresas para identificar pontos de grande potencial e problemas.
Com a análise de dados e o uso do Diagrama de Pareto, é possível identificar os principais influenciadores desses pontos, permitindo análises detalhadas e tomadas de decisão mais efetivas.
O Diagrama de Pareto é crucial para obter insights valiosos, embasar decisões nos dados e direcionar esforços para as áreas de maior impacto.
Hashtag Treinamentos
Para acessar outras publicações de Ciência de Dados, clique aqui!
Expert em conteúdos da Hashtag Treinamentos. Auxilia na criação de conteúdos de variados temas voltados para aqueles que acompanham nossos canais.