Python para Análise de Dados
Tags: analytics, python, pandas, tratamentos
Published: 2021-08-27 18:33:03

De forma geral, a Análise de Dados é um processo de inspeção, coleta, limpeza, transformação de dados, etc. com o objetivo de descobrir informações úteis e solucionar problemas. As Análises de Dados podem ser classificados como: **descritiva**, **preditiva**, **prescritiva** e **diagnóstica**. Mas para este post irei focar na **Análise Descritiva**.
&nbsp;
## Análise Descritiva
&nbsp;
Com a análise descritiva é possível entender o que está acontecendo no negócio atualmente, tendo como principal objetivo resumir, sumarizar e explorar o comportamento dos dados. 
&nbsp;
Neste post irei usar o DataSet do [MovieLens 100k](https://grouplens.org/datasets/movielens/100k/) e responder as seguintes perguntas: 

* **Quais são os 20 filmes mais avaliados?**
* **Quais filmes são mais bem avaliados?**
* **Como estão as classificações dos filmes em relação as idades?**
* **Quais filmes homens e mulheres mais avaliam?**
```python
# Importando a biblioteca Pandas
import pandas as pd
```
**Observação:** A base de dados já foi importada e mesclada com o `Merge`
&nbsp;
```python
# Mesclando o DataFrame 'filme_classificacao' com os 'usuarios'
filme_classificacao = pd.merge(filmes, classificacao)
df = pd.merge(filme_classificacao, usuarios)
df
```
**Observação:** O DataFrame `df` possui 10000 linhas, e para exportar a imagem com `dataframe-image`, a quantidade de linhas precisa diminuir, então criei um novo DataFrame com apenas 10 linhas  
![Alt Text](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/mx2td2lfuqrecfvdgzrf.png)
### **Quais são os 20 filmes mais avaliados?**
```python
avaliados = df['titulo'].value_counts().sort_values(ascending=False)[:20].to_frame('avaliados') \
.style.background_gradient(cmap='Blues')
avaliados
```
![Alt Text](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/ti7z5zs924v86cagfoqw.png)
![Alt Text](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/kii18i5zsg464f6jwnvt.gif)
### Quais filmes mais bem avaliados?
```python
quantidade = df.groupby('titulo').size().to_frame('tamanho')
quantidade
```
![Alt Text](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/sh0608y3axxsttf7me8l.png)
**Observações:** Dentro do DataFrame existe alguns filmes com apenas uma avaliação com classificação máxima (5), isto dificulta nossa análise, então, selecionei os filmes com mais de 100 avaliações feitas por usuários.
```python
quantidade = quantidade[quantidade['tamanho'] > 100]
quantidade
```
![Alt Text](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/v1psxxhl4ysy5n6c0895.png)
Em seguida, criei um novo DataFrame com as médias para cada filme e mesclei com o `Merge`
```python
media = df.groupby('titulo')['classificacao'].mean().to_frame('media').round(2)
media = pd.merge(
    left=quantidade,
    right=media,
    left_index=True,
    right_index=True
)
media
```
![Alt Text](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/biys7003dtzjas9pt2c6.png)
Agora, os mais bem avaliados:
```python
bem_avaliados = media[['tamanho', 'media']].sort_values(by='media', ascending=False)[:10] \
.style.background_gradient(subset=['media'], cmap='YlOrBr')
bem_avaliados
```
![Alt Text](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/6pkex58wrjhj3532j8ar.png)
![Alt Text](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/jrrv5a4dhsj0hogw3h4f.gif)
### Como estão as classificações dos filmes em relação as idades?
&nbsp;
Primeiro vamos plotar um gráfico para ver a distribuição entre as idades dos usuários e usar a **tabela frequência**!
```python
usuarios.idade.plot.hist(bins=30)
plt.title('Distribuição das idades dos usuários')
plt.xlabel('Idades')
plt.ylabel('Quantidades de usuários')
plt.show()
```
![Alt Text](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/vbscajwiaq17qwcg4txk.png)
``` python
frequencia = df.idade.value_counts().to_frame('frequencia')
frequencia = frequencia.reset_index().rename(columns={'index':'idade'}).sort_values(by='idade')
frequencia.index = range(len(frequencia))
frequencia[:28].style.background_gradient(
    subset='frequencia',
    cmap='Greys'
)
```
![Alt Text](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/ejgj7lqev0vd65i2hbm1.png)
Observa-se que as pessoas com **27 anos** foram as que mais classificaram filmes.
&nbsp;
Para visualizarmos as médias das classificações entre as idades, é necessário usar a **distribuição de frequência**, onde o mesmo, mostra um resumo dos dados agrupados em cada faixa. No nosso caso, as idades contém muitos valores elencados, então para isso, usaremos as **classes** para reduzir a quantidade desses valores agrupando-os em intervalos.
&nbsp;
**Amplitude Total:** 66 
&nbsp;
Para escolher a quantidade de classes, usei a **Fórmula de Sturges.**
&nbsp;
**Classes:** 8
&nbsp;
**Amplitude do intervalo:** 9
&nbsp;
```python
labels = ['7-16', '17-26', '27-36', '37-46', '47-56', '48-57', '58-67', '68-77']
df['idade_agrup'] = pd.cut(df.idade, range(0, 81, 10), right=False, labels=labels)
df[['idade', 'idade_agrup']].drop_duplicates()[:15]
```
![Alt Text](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/8fvw835lcfgwkablu6i0.png)
&nbsp;
Agora analisando as médias das idades agrupadas:
```python
df.groupby('idade_agrup').agg({'classificacao': [np.size, np.mean]}).round(2)
```
![Alt Text](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/bkagxbyslo9a8r57tzeq.png)
Vejamos como os filmes são avaliados em cada faixa etária:
```python
classficacao_media = df.loc[filmes_50.index].groupby(['titulo', 'idade_agrup'])
classficacao_media.classificacao.mean().head(15)
```
![Alt Text](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/yk254k37wnz75q8y1ves.png)
**Observe-se** que tanto a faixa etária quanto título são índices aqui; como consequência irá produzir uma lista muito grande e para transformar em uma tabela mais visual irei utilizar o **unstack**
```
classificacao_media.classificacao.mean().unstack(1).fillna(0)[10:20]
```
![Alt Text](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/iiprsc3tfagkjwt7jprm.png)
&nbsp;
**Quais filmes homens e mulheres mais avaliam?**
&nbsp;
Para isso, usarei o **pivot_table**:
```python
pivot = df.pivot_table(index=['filme_id', 'titulo'],
                      columns=['sexo'],
                      values='classificacao',
                      fill_value=0)
```
![Alt Text](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/a55aaqg9i6zv3z51va0t.png)
Diferença entra as médias:
```python
pivot['diff'] = pivot.M - pivot.F
```
![Alt Text](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/0r1ztdvhliu0xttn66p3.png)
&nbsp;
```python
pivot.reset_index('filme_id', inplace=True)
divergencia = pivot[pivot.filme_id.isin(filmes_50.index)]['diff']
divergencia.sort_values().plot(kind='barh', figsize=[9, 15])
plt.title('Média masculina vs. feminino')
plt.ylabel('Título')
plt.xlabel('Diferença de avaliação média');
```
![Alt Text](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/2ox3fbnab1d74h6tieit.png)