Dropna By Column по уровням в мультииндексах и своп для значений не-na - PullRequest
1 голос
/ 25 июня 2019

Я пытаюсь сделать некоторые преобразования и вроде застрял. Надеюсь, кто-нибудь поможет мне здесь.

l0    a         b         c         d       e         f      
l1    1     2   1   2     1     2   1   2   1   2     1     2
0   NaN   NaN NaN NaN  93.4   NaN NaN NaN NaN NaN  19.0  28.9
1   NaN   9.0 NaN NaN  43.5  32.0 NaN NaN NaN NaN   NaN   3.4
2   NaN   5.0 NaN NaN  93.3  83.6 NaN NaN NaN NaN  59.5  28.2
3   NaN  19.6 NaN NaN  72.8  47.4 NaN NaN NaN NaN  31.5  67.2
4   NaN   NaN NaN NaN   NaN  62.5 NaN NaN NaN NaN   NaN   1.8

У меня есть датафрейм (показан выше), и, как вы можете видеть, есть несколько 'NaN' с многоиндексным столбцом. Выбор столбцов вдоль уровня = 0 (т.е. l0)

  1. Я хотел бы удалить весь столбец, если все NaN . так что в этом случае столбец
l0 = ['b', 'd', 'e'] # drop-cols

должен быть удален из кадра данных

l0    a           c           f      
l1    1     2     1     2     1     2
0   NaN   NaN  93.4   NaN  19.0  28.9
1   NaN   9.0  43.5  32.0   NaN   3.4
2   NaN   5.0  93.3  83.6  59.5  28.2
3   NaN  19.6  72.8  47.4  31.5  67.2
4   NaN   NaN   NaN  62.5   NaN   1.8
  1. Это даст мне фрейм данных (как показано выше). Я бы хотел затем slide значения вдоль строк, если все записи до этого являются нулевыми (или менять значения между соседними столбцами). например Глядя на индекс = 0 то есть первый ряд.
l0    a           c           f      
l1    1     2     1     2     1     2
0   NaN   NaN  93.4   NaN  19.0  28.9

Так как все значения в col - a равны нулю. Я хотел бы сначала сдвинуть / изменить значения ч / б col - a и col - c а затем повторите то же самое для столбцов вдоль right-side, т.е. замените записи в col-c на col-f и сделайте все записи в col-f, NaN, давая мне

l0    a           c           f      
l1    1     2     1     2     1     2
0   93.4   NaN  19.0  28.9  NaN   NaN

Это действительно для экономии памяти для обработки и хранения информации, поскольку чередование меток ['a', 'b', 'c'...] не меняет смысла данных.

РЕДАКТИРОВАТЬ: Любая идея для (2)

Мне удалось решить (1) с помощью следующего кода:

for c in df.columns.get_level_values(0).unique():
  if df[c].isna().all().all():
    df = df.drop(columns=[c])
df

Ответы [ 2 ]

1 голос
/ 26 июня 2019

groupby и filter

df.groupby(axis=1, level=0).filter(lambda d: ~d.isna().all().all())

    a           c           f      
    1     2     1     2     1     2
0 NaN   NaN  93.4   NaN  19.0  28.9
1 NaN   9.0  43.5  32.0   NaN   3.4
2 NaN   5.0  93.3  83.6  59.5  28.2
3 NaN  19.6  72.8  47.4  31.5  67.2
4 NaN   NaN   NaN  62.5   NaN   1.8

немного короче

df.groupby(axis=1, level=0).filter(lambda d: ~np.all(d.isna()))
1 голос
/ 25 июня 2019

Вы можете сделать с all

s=df.isnull().all(level=0,axis=1).all()
df.drop(s.index[s],axis=1,level=0)
Out[55]: 
     a           c           f      
     1     2     1     2     1     2
l1                                  
0  NaN   NaN  93.4   NaN  19.0  28.9
1  NaN   9.0  43.5  32.0   NaN   3.4
2  NaN   5.0  93.3  83.6  59.5  28.2
3  NaN  19.6  72.8  47.4  31.5  67.2
4  NaN   NaN   NaN  62.5   NaN   1.8
...