Tengo un marco de datos:

import pandas as pd 
import numpy as np 
data = pd.DataFrame({'file':['file1','file1','file1','file2','file2','file2' ], 'x': [1,2,3,1,2,4], 'y': [10,20,30,10, 20, 40], 'norm_y': [2,4,6,2,4,8]})

print (data)

out: 
    file  x   y  norm_y
0  file1  1  10       2
1  file1  2  20       4
2  file1  3  30       6
3  file2  1  10       2
4  file2  2  20       4
5  file2  4  40       8

Quiero imprimirlo para que:

  • el archivo es el índice principal
  • x, y, z son el subíndice

Para que se vea así:

    file          
0         x     1  2  3
1  file1  y     10 20 30
2         ynorm 2  4  6
3         x     1  2  4
4  file2  y     10 20 40
5         ynorm 2  4  8

Creo que la respuesta será algo como:

  • establecer el índice de fila: data.set_index (['archivo'])
  • transponer las columnas x, y, ynorm
0
David 8 7 oct. 2019 a las 20:01

5 respuestas

La mejor respuesta

En esencia, este es un problema pivot, pero no es realmente sencillo.


df.assign(
  key=df.groupby('file').cumcount()).set_index(['file', 'key']).stack().unstack('key')
key            0   1   2
file
file1 x        1   2   3
      y       10  20  30
      norm_y   2   4   6
file2 x        1   2   4
      y       10  20  40
      norm_y   2   4   8
3
user3483203 7 oct. 2019 a las 17:15

Usted puede hacer:

df['col' ] = df.groupby('file').cumcount()+1
df.pivot_table(index='file', columns='col').stack(level=0)

Salida:

col            1   2   3
file                    
file1 norm_y   2   4   6
      x        1   2   3
      y       10  20  30
file2 norm_y   2   4   8
      x        1   2   4
      y       10  20  40
2
Quang Hoang 7 oct. 2019 a las 17:17

Jugando con formas numpy

fil, var, val = df.melt('file').values.T

new = pd.DataFrame(np.hstack([fil.reshape(-1,3)[:, 0].reshape(-1,1), 
                              var.reshape(-1,3)[:, 0].reshape(-1,1), 
                              val.reshape(-1,3)]))\
        .set_index([0,1])\
        .sort_index()

               2   3   4
0     1                 
file1 norm_y   2   4   6
      x        1   2   3
      y       10  20  30
file2 norm_y   2   4   8
      x        1   2   4
      y       10  20  40
1
rafaelc 7 oct. 2019 a las 17:29

Solo necesitas un poco de imaginación:

data.set_index('file').groupby(level=0).apply(lambda x: x.T)

Salida:

file          file2  file2  file2
file                             
file1 x           1      2      3
      y          10     20     30
      norm_y      2      4      6
file2 x           1      2      4
      y          10     20     40
      norm_y      2      4      8
3
ansev 7 oct. 2019 a las 17:29

Prueba esto.

(
    pd.melt(data, id_vars='file', value_vars=['x', 'y', 'norm_y']) #Unstacks the data
    .groupby(['file', 'variable'])['value'] #restacks with file and variable as index
    .aggregate(lambda x: tuple(x)) #splits out values in to a column
    .apply(pd.Series) #turns them into separate columns
)
0
eljusticiero67 7 oct. 2019 a las 17:30
58274092