Страницы

Поиск по вопросам

пятница, 7 июня 2019 г.

Как распределить неопределенную категорию в фиче пропорционально долям известных категорий?

Есть датафрейм df. Есть фича feat имеющая три категории cat1, cat2, и немногочисленная Unknown.
Я хочу избавиться от Unknown, раскидав ее по cat1 и cat2 так, чтобы она разлетелась по ним пропорционально их доле в датасете. То есть, если изначально было 45% cat1, 40% cat2 и 5% Unknown, то нужно, чтобы Unknown разлетелась в между cat1 и сat2 в соотношении 9/8.
В документации и блогах ничего подобного не нашел.


Ответ

Исходный DF:
In [67]: %paste df = pd.DataFrame({'feat':np.random.choice(['cat1','cat2','Unknown'], size=100, p=[0.45,0.40,0.15])}) ## -- End pasted text --
In [68]: df.feat.value_counts() Out[68]: cat1 49 cat2 36 Unknown 15 Name: feat, dtype: int64
Сначала найдем соотношение между cat1 и cat2
In [69]: pct = df.feat.value_counts() / len(df)
In [70]: ratio = pct.loc[['cat1','cat2']].min() / pct.loc[['cat1','cat2']].max()
In [71]: pct Out[71]: cat1 0.49 cat2 0.36 Unknown 0.15 Name: feat, dtype: float64
In [72]: ratio Out[72]: 0.7346938775510204
теперь заменим строки с Unknown с таким же соотношением:
In [74]: df.loc[df['feat']=='Unknown', 'feat'] = \ ...: np.random.choice([pct[['cat1','cat2']].idxmax(), pct[['cat1','cat2']].idxmin()], ...: size=df['feat'].eq('Unknown').sum(), ...: p=[ratio, 1-ratio]) ...: ...:
In [75]: df.feat.value_counts() Out[75]: cat1 62 cat2 38 Name: feat, dtype: int64
проверка соотношения после замены значений:
In [76]: pct.loc[['cat1','cat2']].min() / pct.loc[['cat1','cat2']].max() Out[76]: 0.7346938775510204

Комментариев нет:

Отправить комментарий