Organizar datos con pandas I

junio 18, 2015

 

Organizar datos con pandas I

In [1]:
import pandas as pd
import numpy as np

Multi-índice en dataframe

Crear un dataframe con multi-índice

Los dataframes pueden tener varios índices y varios nombres de columna, para esto se usa la clase de pandas MultiIndex. Estos se pueden crear a partir de una lista de tuplas, con el método drom_tuples, donde cada tupla contiene los nombres de cada columna o a partir de una combinación entre varias tuplas con el método from_product
In [2]:
columns = pd.MultiIndex.from_tuples([('A', 'positivo'), ('B', 'positivo'), 
                                     ('A', 'negativo'), ('B', 'negativo'), 
                                     ('O', 'positivo')], 
                                     names=['tipo', 'Rh'])
index = pd.MultiIndex.from_product([('menor', 'adulto'),('hombre', 'mujer')], 
                                   names=['edad', 'sexo'])
df = pd.DataFrame(np.random.randn(4,5), columns=columns, index=index)
df
Out[2]:
tipo A B A B O
Rh positivo positivo negativo negativo positivo
edad sexo
menor hombre -1.807191 -1.048591 0.458959 0.349050 0.682837
mujer -0.769500 -0.541011 -0.628476 -0.847258 -0.576029
adulto hombre 0.083071 0.346534 1.641367 0.563324 0.806927
mujer -1.183561 0.254588 0.546878 1.816080 1.309236
4 rows × 5 columns

Obtener información de un dataframe multi-índex

Columnas

Para obtener la información de una columna se usa el formato corriente, dataframe[nombre_col], siempre y cuando el nombre de la columna pertenezca a una columna de primer nivel, es decir, la primera fila de nombres de columnas.
In [3]:
df['A']
Out[3]:
Rh positivo negativo
edad sexo
menor hombre -1.807191 0.458959
mujer -0.769500 -0.628476
adulto hombre 0.083071 1.641367
mujer -1.183561 0.546878
4 rows × 2 columns
Para obtener información de las columnas de otros niveles, se debe referir primero la columna de primer nivel y luego a las de los niveles siguientes, en órden jerárquico.
In [4]:
df['B', 'positivo']
Out[4]:
edad    sexo  
menor   hombre   -1.048591
        mujer    -0.541011
adulto  hombre    0.346534
        mujer     0.254588
Name: (B, positivo), dtype: float64

Filas

Las filas se obtienen usando los métodos loc, iloc y ix. De igual forma que las columnas, se acata el orden jerárquico hasta llegar a los datos deseados.
In [5]:
df.loc['adulto']
Out[5]:
tipo A B A B O
Rh positivo positivo negativo negativo positivo
sexo
hombre 0.083071 0.346534 1.641367 0.563324 0.806927
mujer -1.183561 0.254588 0.546878 1.816080 1.309236
2 rows × 5 columns
In [6]:
df.loc['adulto', 'mujer']
Out[6]:
tipo  Rh      
A     positivo   -1.183561
B     positivo    0.254588
A     negativo    0.546878
B     negativo    1.816080
O     positivo    1.309236
Name: (adulto, mujer), dtype: float64
Por posición:
In [7]:
df.iloc[0]
Out[7]:
tipo  Rh      
A     positivo   -1.807191
B     positivo   -1.048591
A     negativo    0.458959
B     negativo    0.349050
O     positivo    0.682837
Name: (menor, hombre), dtype: float64
In [8]:
df.iloc[0, 1]
Out[8]:
-1.0485906955417377

Slice (seleccionar secciones del dataframe)

In [9]:
df
Out[9]:
tipo A B A B O
Rh positivo positivo negativo negativo positivo
edad sexo
menor hombre -1.807191 -1.048591 0.458959 0.349050 0.682837
mujer -0.769500 -0.541011 -0.628476 -0.847258 -0.576029
adulto hombre 0.083071 0.346534 1.641367 0.563324 0.806927
mujer -1.183561 0.254588 0.546878 1.816080 1.309236
4 rows × 5 columns
In [10]:
df.iloc[1:3]
Out[10]:
tipo A B A B O
Rh positivo positivo negativo negativo positivo
edad sexo
menor mujer -0.769500 -0.541011 -0.628476 -0.847258 -0.576029
adulto hombre 0.083071 0.346534 1.641367 0.563324 0.806927
2 rows × 5 columns

General

Para obtener información sea de filas o columnas de cualquier nivel se usa el método xs. Se especifica el nombre de la columna y el nombre del nivel al que pertenece, para buscar por columna se agrega axis=1.
In [11]:
df.xs('mujer', level='sexo')
Out[11]:
tipo A B A B O
Rh positivo positivo negativo negativo positivo
edad
menor -0.769500 -0.541011 -0.628476 -0.847258 -0.576029
adulto -1.183561 0.254588 0.546878 1.816080 1.309236
2 rows × 5 columns
In [12]:
df.xs('negativo', level='Rh', axis=1)
Out[12]:
tipo A B
edad sexo
menor hombre 0.458959 0.349050
mujer -0.628476 -0.847258
adulto hombre 1.641367 0.563324
mujer 0.546878 1.816080
4 rows × 2 columns
Si se quiere mantener la información de los otros niveles a los que pertenece esta información se usa el argumento drop_level=False
In [13]:
df.xs('negativo', level='Rh', axis=1 , drop_level=False)
Out[13]:
tipo A B
Rh negativo negativo
edad sexo
menor hombre 0.458959 0.349050
mujer -0.628476 -0.847258
adulto hombre 1.641367 0.563324
mujer 0.546878 1.816080
4 rows × 2 columns

Stack

El método stack permite reordenar los datos que tienen iguales atributos con igual nombre de columna en el dataframe. Por ejemplo si se tienen algún tipo de resultados para varios tipos de sangre, los tipos pueden ser diferentes pero pueden compartir el Rh, ese sería un atributo en común. También es uno de los métodos para manipular dataframe con varios nombres de columna.
In [14]:
# Si no se le indica los nombres de columna que convertirá en índice este 
# toma el último nivel de columna en este caso "tipo" es el primer nivel 
# y "Rh" el segundo.
df.stack()
Out[14]:
tipo A B O
edad sexo Rh
menor hombre negativo 0.458959 0.349050 NaN
positivo -1.807191 -1.048591 0.682837
mujer negativo -0.628476 -0.847258 NaN
positivo -0.769500 -0.541011 -0.576029
adulto hombre negativo 1.641367 0.563324 NaN
positivo 0.083071 0.346534 0.806927
mujer negativo 0.546878 1.816080 NaN
positivo -1.183561 0.254588 1.309236
8 rows × 3 columns
In [15]:
df.stack('tipo')
Out[15]:
Rh negativo positivo
edad sexo tipo
menor hombre A 0.458959 -1.807191
B 0.349050 -1.048591
O NaN 0.682837
mujer A -0.628476 -0.769500
B -0.847258 -0.541011
O NaN -0.576029
adulto hombre A 1.641367 0.083071
B 0.563324 0.346534
O NaN 0.806927
mujer A 0.546878 -1.183561
B 1.816080 0.254588
O NaN 1.309236
12 rows × 2 columns
In [16]:
# Se convierten los dos nombres de columna a índice tomando como principal a "tipo" y 
# "Rh" como una clasificación interna de este.
df_st = df.stack(level=['tipo','Rh'])
df_st
Out[16]:
edad    sexo    tipo  Rh      
menor   hombre  A     negativo    0.458959
                      positivo   -1.807191
                B     negativo    0.349050
                      positivo   -1.048591
                O     positivo    0.682837
        mujer   A     negativo   -0.628476
                      positivo   -0.769500
                B     negativo   -0.847258
                      positivo   -0.541011
                O     positivo   -0.576029
adulto  hombre  A     negativo    1.641367
                      positivo    0.083071
                B     negativo    0.563324
                      positivo    0.346534
                O     positivo    0.806927
        mujer   A     negativo    0.546878
                      positivo   -1.183561
                B     negativo    1.816080
                      positivo    0.254588
                O     positivo    1.309236
dtype: float64
In [17]:
# Ahora "tipo" como una clasificación interna de "Rh"
df.stack(level=['Rh','tipo'])
Out[17]:
edad    sexo    Rh        tipo
menor   hombre  negativo  A       0.458959
                          B       0.349050
                positivo  A      -1.807191
                          B      -1.048591
                          O       0.682837
        mujer   negativo  A      -0.628476
                          B      -0.847258
                positivo  A      -0.769500
                          B      -0.541011
                          O      -0.576029
adulto  hombre  negativo  A       1.641367
                          B       0.563324
                positivo  A       0.083071
                          B       0.346534
                          O       0.806927
        mujer   negativo  A       0.546878
                          B       1.816080
                positivo  A      -1.183561
                          B       0.254588
                          O       1.309236
dtype: float64

You Might Also Like

0 comments

Apoyado por: