May 19, 2022

Заполнение пропусков с Pandas

Рассмотрим, основные способы заполнения пропусков с Pandas. В демонстрационных целях создадим датафрейм:

import pandas as pd
import numpy as np

df = pd.DataFrame({'gr':[1,2,1,2,2,2,1],
                   'month':[pd.Period('2021-01', freq='M'), pd.Period('2021-01', freq='M'), 
                            pd.Period('2021-05', freq='M'), pd.Period('2021-05', freq='M'),
                            pd.Period('2021-04', freq='M'), pd.Period('2021-02', freq='M'), 
                            pd.Period('2021-08', freq='M')],
                   'val1':[np.nan, 6, 3, np.nan, np.nan, 8, -5],
                   'val2':[1, np.nan, 3, 2, -9, 3, np.nan],
                   'val3':[0, np.nan, 1, 1, 1, 1, np.nan]}, index=['one', 'two', 'three', 'four', 'five', 
                                                                   'six', 'seven'])

df

Заполнение чаще всего осуществляется с помощью метода fillna. Распространенным способом является вставка на место пропусков некоторого фиксированного значения (в fillna можно передать словарь, в котором указать для каждого столбца такое значение):

df.fillna({'val1':1, 'val2':2})

Также популярно заполнение значениями из предшествующей (аргумент method='bfill') либо последующей записи (method='ffill'):

df.fillna(method='bfill')

Следует отметить, что для аналогичных действий имеются специальные методы с названиями bfill и ffill:

df.ffill()

Более сложным кейсом является заполнение значений с учетом группы, к которой принадлежит объект. Например, пусть она определяется колонкой 'gr', а время столбцом 'month', и вы хотите заполнить пропуски более ранними значениями в колонках. Тогда сначала отсортируйте датафрейм по дате:

df.sort_values(by='month', inplace=True)
df

После аналогичные методы можно вызывать на сгруппированных объектах:

df.groupby('gr')[['val1', 'val2']].ffill()

то же с fillna:

df.groupby('gr')[['val1', 'val2']].fillna(method='ffill')

Распространенным вариантом является заполнение в одну сторону, затем в другую. Это можно сделать с методом apply:

df.groupby('gr')[['val1', 'val2']].apply(lambda x: x.bfill().ffill())

или с методом transform:

df.groupby('gr')[['val1', 'val2']].transform(lambda x: x.bfill().ffill())

Не пропустите ничего интересного и подписывайтесь на страницы канала в других социальных сетях:

Яндекс Дзен

Telegram