Manipulação de Dados com Pandas

Author

Vinícius Oviedo

Agregações

Nesta aula, vamos trabalhar com agregação de dados com Pandas. É uma aula mais curta, comparada às anteriores, porém permite um leque de possibilidades. Veremos:

  1. Método groupby
  2. Método agg

Para isso, utilizaremos o conjunto de dados sobre vendas.

import pandas as pd

vendas_europa = pd.read_csv('dados/vendas/EuropeSalesRecords.csv')
vendas_europa.head()
Region Country Item Type Sales Channel Order Priority Order Date Order ID Ship Date Units Sold Unit Price Unit Cost Total Revenue Total Cost Total Profit
0 Europe Czech Republic Beverages Offline C 9/12/2011 478051030 9/29/2011 4778 47.45 31.79 226716.10 151892.62 74823.48
1 Europe Bosnia and Herzegovina Clothes Online M 10/14/2013 919133651 11/4/2013 927 109.28 35.84 101302.56 33223.68 68078.88
2 Europe Austria Cereal Offline C 8/13/2014 987410676 9/6/2014 5616 205.70 117.11 1155211.20 657689.76 497521.44
3 Europe Bulgaria Office Supplies Online L 10/31/2010 672330081 11/29/2010 6266 651.21 524.96 4080481.86 3289399.36 791082.50
4 Europe Estonia Fruits Online L 9/28/2016 579463422 11/1/2016 4958 9.33 6.92 46258.14 34309.36 11948.78

1. Método groupby()

Nesse método, podemos agrupar dados com base em categorias e precisamos obrigatoriamente informar uma medida de agregação (e.g, soma, média, mediana, desvio padrão, etc.). Começemos com uma pergunta de negócio.

Qual foi o faturamento total por país? (usemos 1 casas decimal)

vendas_europa.groupby('Country')['Total Revenue'].sum().round(1)
Country
Albania                   32224853.9
Andorra                   47756693.2
Armenia                   37519840.2
Austria                   35740871.5
Belarus                   34236260.8
Belgium                   25852572.3
Bosnia and Herzegovina    50117508.5
Bulgaria                  38161555.7
Croatia                   27348195.7
Cyprus                    33008851.5
Czech Republic            53543932.1
Denmark                   26968532.5
Estonia                   23410001.8
Finland                   26027949.0
France                    39362112.2
Georgia                   22802195.7
Germany                   38055087.6
Greece                    38699541.7
Hungary                   42408249.1
Iceland                   25570227.4
Ireland                   33022223.3
Italy                     35878352.1
Kosovo                    53833142.8
Latvia                    38722084.2
Liechtenstein             29872564.4
Lithuania                 29031942.1
Luxembourg                33075377.2
Macedonia                 49222085.2
Malta                     47145320.8
Moldova                   27031700.1
Monaco                    13828738.2
Montenegro                31346476.9
Netherlands               20860788.8
Norway                    31520698.5
Poland                    33805403.2
Portugal                  47172189.8
Romania                   34286150.8
Russia                    46051659.8
San Marino                47883708.5
Serbia                    42193537.7
Slovakia                  42940998.3
Slovenia                  38892531.3
Spain                     27644278.7
Sweden                    35482128.0
Switzerland               31875174.0
Ukraine                   53252317.5
United Kingdom            26654989.5
Vatican City              22280804.1
Name: Total Revenue, dtype: float64

Note que country veio como inídice, mas podemos deixar as categorias como linhas convencionais (usando as_index=False) e adicionar mais de uma categoria. Para isso, vamos responder a outra pergunta.

Qual foi o lucro médio em cada país por canal de venda? listemos o top 5

# Agregação:
lucro_medio_pais_e_canal = vendas_europa.groupby('Country', as_index=False)['Total Profit'].sum().round(1)

# Ordenação dos dados:
lucro_medio_pais_e_canal = lucro_medio_pais_e_canal.sort_values(
  by='Total Profit', ascending=False
)

# Visualização dos resultados:
lucro_medio_pais_e_canal.head()
Country Total Profit
1 Andorra 15410036.6
45 Ukraine 14804925.7
28 Malta 14610127.9
22 Kosovo 14409145.4
38 San Marino 13792992.8

2. Método agg

Esse metodo serve para utilizarmos mais de uma medida de agregação. No caso da pergunta anterior, só a média não nos diz muita coisa. Em outras palavras, é uma boa prática mostrar o desvio padrão junto à média. Assim, temos uma noção da variabilidade dos dados e se a média de fato representa bem nosso conjunto de dados. Vamos utilizar a mesma lógica da pergunta anterior, mas mostrando os 5 piores em termos de lucro.

# Agregação:
vendas_europa.groupby(['Country', 'Sales Channel'])['Total Profit']\
  .agg(['mean', 'std', 'median']).tail()
mean std median
Country Sales Channel
Ukraine Online 540192.216250 461192.942092 419867.210
United Kingdom Offline 386919.697143 400336.448858 250574.940
Online 413617.145625 457835.010825 216474.465
Vatican City Offline 262827.323125 298981.868340 115792.650
Online 315512.177143 197270.837319 272952.500

Outra opção é:

# Agregação:
vendas_europa.groupby(['Country', 'Sales Channel'])['Total Profit'].describe()
count mean std min 25% 50% 75% max
Country Sales Channel
Albania Offline 11.0 614448.018182 612231.249278 35454.24 79415.0400 543430.340 890054.8050 1672455.53
Online 10.0 373177.782000 399647.088296 17601.84 63175.9350 229644.635 625957.5150 1107843.75
Andorra Offline 18.0 249127.326111 315220.845804 2369.03 25045.9475 126314.510 413880.4275 1245958.14
Online 22.0 496624.761818 497687.329727 24194.70 108122.5350 347167.260 712274.5800 1700448.60
Armenia Offline 16.0 385731.609375 347925.918412 8492.84 91203.5000 402212.320 499465.2850 1236511.53
... ... ... ... ... ... ... ... ... ...
Ukraine Online 16.0 540192.216250 461192.942092 28141.02 172150.1700 419867.210 767868.0850 1574045.11
United Kingdom Offline 7.0 386919.697143 400336.448858 17568.90 131640.1800 250574.940 491785.0000 1193443.68
Online 16.0 413617.145625 457835.010825 9033.12 77568.1000 216474.465 598346.2875 1531273.09
Vatican City Offline 16.0 262827.323125 298981.868340 16419.33 44425.1150 115792.650 385834.8300 1016587.82
Online 7.0 315512.177143 197270.837319 52429.68 196048.0750 272952.500 449443.3750 592220.16

96 rows × 8 columns