python - with - Ambigüedad en la definición de "eje" de Dataframe de Pandas/Numpy Array
pandas python (5)
He estado muy confundido acerca de cómo se definen los ejes de python y si se refieren a las filas o columnas de un DataFrame. Considere el siguiente código:
>>> df = pd.DataFrame([[1, 1, 1, 1], [2, 2, 2, 2], [3, 3, 3, 3]], columns=["col1", "col2", "col3", "col4"])
>>> df
col1 col2 col3 col4
0 1 1 1 1
1 2 2 2 2
2 3 3 3 3
Entonces, si llamamos a
df.mean(axis=1)
, obtendremos una media entre las filas:
>>> df.mean(axis=1)
0 1
1 2
2 3
Sin embargo, si llamamos
df.drop(name, axis=1)
, en realidad
soltamos una columna
, no una fila:
>>> df.drop("col4", axis=1)
col1 col2 col3
0 1 1 1
1 2 2 2
2 3 3 3
¿Alguien puede ayudarme a comprender qué se entiende por "eje" en pandas / numpy / scipy?
Una nota al
DataFrame.mean
,
DataFrame.mean
podría definirse incorrectamente.
En la documentación de
DataFrame.mean
que se
DataFrame.mean
que
axis=1
significa una media sobre las columnas, no las filas ...
Cuando axis = ''rows'' o axis = 0, significa elementos de acceso en la dirección de las filas, de arriba a abajo. Si aplica la suma a lo largo del eje = 0, nos dará totales de cada columna.
Cuando axis = ''columnas'' o axis = 1, significa elementos de acceso en la dirección de las columnas, de izquierda a derecha. Si aplicamos suma a lo largo del eje = 1, obtendremos totales de cada fila.
Todavía confuso! Pero lo anterior lo hace un poco más fácil para mí.
Debería ser más conocido que los alias de cadena ''índice'' y ''columnas'' pueden usarse en lugar de los enteros 0/1. Los alias son mucho más explícitos y me ayudan a recordar cómo se realizan los cálculos. Otro alias para ''índice'' es ''filas'' .
Cuando se utiliza
axis=''index''
, los cálculos se realizan en las columnas, lo cual es confuso.
Pero, lo recuerdo como obtener un resultado que es del mismo tamaño que otra fila.
Veamos algunos datos en la pantalla para ver de qué estoy hablando:
df = pd.DataFrame(np.random.rand(10, 4), columns=list(''abcd''))
a b c d
0 0.990730 0.567822 0.318174 0.122410
1 0.144962 0.718574 0.580569 0.582278
2 0.477151 0.907692 0.186276 0.342724
3 0.561043 0.122771 0.206819 0.904330
4 0.427413 0.186807 0.870504 0.878632
5 0.795392 0.658958 0.666026 0.262191
6 0.831404 0.011082 0.299811 0.906880
7 0.749729 0.564900 0.181627 0.211961
8 0.528308 0.394107 0.734904 0.961356
9 0.120508 0.656848 0.055749 0.290897
Cuando queremos tomar la media de todas las columnas, usamos
axis=''index''
para obtener lo siguiente:
df.mean(axis=''index'')
a 0.562664
b 0.478956
c 0.410046
d 0.546366
dtype: float64
Se obtendría el mismo resultado:
df.mean() # default is axis=0
df.mean(axis=0)
df.mean(axis=''rows'')
Para usar una operación de izquierda a derecha en las filas, use axis = ''columnas''. Lo recuerdo pensando que se puede agregar una columna adicional a mi DataFrame:
df.mean(axis=''columns'')
0 0.499784
1 0.506596
2 0.478461
3 0.448741
4 0.590839
5 0.595642
6 0.512294
7 0.427054
8 0.654669
9 0.281000
dtype: float64
Se obtendría el mismo resultado:
df.mean(axis=1)
Agregue una nueva fila con axis = 0 / index / rows
Usemos estos resultados para agregar filas o columnas adicionales para completar la explicación. Entonces, siempre que use axis = 0 / index / rows, es como obtener una nueva fila del DataFrame. Agreguemos una fila:
df.append(df.mean(axis=''rows''), ignore_index=True)
a b c d
0 0.990730 0.567822 0.318174 0.122410
1 0.144962 0.718574 0.580569 0.582278
2 0.477151 0.907692 0.186276 0.342724
3 0.561043 0.122771 0.206819 0.904330
4 0.427413 0.186807 0.870504 0.878632
5 0.795392 0.658958 0.666026 0.262191
6 0.831404 0.011082 0.299811 0.906880
7 0.749729 0.564900 0.181627 0.211961
8 0.528308 0.394107 0.734904 0.961356
9 0.120508 0.656848 0.055749 0.290897
10 0.562664 0.478956 0.410046 0.546366
Agregar una nueva columna con axis = 1 / columnas
Del mismo modo, cuando axis = 1 / columnas creará datos que se pueden convertir fácilmente en su propia columna:
df.assign(e=df.mean(axis=''columns''))
a b c d e
0 0.990730 0.567822 0.318174 0.122410 0.499784
1 0.144962 0.718574 0.580569 0.582278 0.506596
2 0.477151 0.907692 0.186276 0.342724 0.478461
3 0.561043 0.122771 0.206819 0.904330 0.448741
4 0.427413 0.186807 0.870504 0.878632 0.590839
5 0.795392 0.658958 0.666026 0.262191 0.595642
6 0.831404 0.011082 0.299811 0.906880 0.512294
7 0.749729 0.564900 0.181627 0.211961 0.427054
8 0.528308 0.394107 0.734904 0.961356 0.654669
9 0.120508 0.656848 0.055749 0.290897 0.281000
Parece que puede ver todos los alias con las siguientes variables privadas:
df._AXIS_ALIASES
{''rows'': 0}
df._AXIS_NUMBERS
{''columns'': 1, ''index'': 0}
df._AXIS_NAMES
{0: ''index'', 1: ''columns''}
Otra forma de explicar:
// Not realistic but ideal for understanding the axis parameter
df = pd.DataFrame([[1, 1, 1, 1], [2, 2, 2, 2], [3, 3, 3, 3]],
columns=["idx1", "idx2", "idx3", "idx4"],
index=["idx1", "idx2", "idx3"]
)
---------------------------------------1
| idx1 idx2 idx3 idx4
| idx1 1 1 1 1
| idx2 2 2 2 2
| idx3 3 3 3 3
0
Acerca de
df.drop
(eje significa la posición)
A: I wanna remove idx3.
B: **Which one**? // typing while waiting response: df.drop("idx3",
A: The one which is on axis 1
B: OK then it is >> df.drop("idx3", axis=1)
// Result
---------------------------------------1
| idx1 idx2 idx4
| idx1 1 1 1
| idx2 2 2 2
| idx3 3 3 3
0
Acerca de
df.apply
(eje significa dirección)
A: I wanna apply sum.
B: Which direction? // typing while waiting response: df.apply(lambda x: x.sum(),
A: The one which is on *parallel to axis 0*
B: OK then it is >> df.apply(lambda x: x.sum(), axis=0)
// Result
idx1 6
idx2 6
idx3 6
idx4 6
Quizás sea más simple recordarlo como 0 = abajo y 1 = de lado a lado .
Esto significa:
-
Use
axis=0
para aplicar un método en cada columna o en las etiquetas de fila (el índice). -
Utilice
axis=1
para aplicar un método en cada fila o en las etiquetas de columna.
Aquí hay una imagen para mostrar las partes de un DataFrame a las que se refiere cada eje:
También es útil recordar que Pandas sigue el uso de NumPy del
axis
de la palabra.
El uso se explica en el
glosario de términos de
NumPy:
Los ejes se definen para matrices con más de una dimensión. Una matriz bidimensional tiene dos ejes correspondientes: el primero que corre verticalmente hacia abajo a través de las filas (eje 0) , y el segundo que corre horizontalmente a través de las columnas (eje 1) . [ mi énfasis ]
Entonces, con respecto al método en la pregunta,
df.mean(axis=1)
, parece estar correctamente definido.
Toma la media de las entradas
horizontalmente a través de las columnas
, es decir, a lo largo de cada fila individual.
Por otro lado,
df.mean(axis=0)
sería una operación que actúa verticalmente
hacia abajo a través de las filas
.
De manera similar,
df.drop(name, axis=1)
refiere a una acción en las etiquetas de columna, porque intuitivamente atraviesan el eje horizontal.
Especificar
axis=0
haría que el método actúe en filas en su lugar.
Ya hay respuestas correctas, pero te doy otro ejemplo con> 2 dimensiones.
El
axis
parámetro significa el
eje a cambiar
.
Por ejemplo, considere que hay un marco de datos con dimensión
axbxc
.
-
df.mean(axis=1)
devuelve un marco de datos con dimensión ax 1 xc . -
df.drop("col4", axis=1)
devuelve un marco de datos con la dimensión ax (b-1) xc .