Я пытаюсь отсканировать фрейм данных Pandas и определить все столбцы, которые являются истинными для определенной строки, и агрегировать имена столбцов в выходном столбце.
Учитывая пример ввода следующим образом:
a b c
True False True
True False False
Цель состоит в том, чтобы добиться следующего результата:
a b c output
True False True ['a', 'c']
True False False ['a']
Моя попытка заключалась в использовании np.where, как показано ниже, но это довольно неэффективно для масштабирования.
df['output_1'] = np.where(df['a']==True, 'a', '')
df['output_2'] = np.where(df['b']==True, 'b', '')
df['output_3'] = np.where(df['c']==True, 'c', '')
df['output'] = df['output_1'] + df['output_2'] + df['output_3']






Вы можете использовать растопить
Данные:
data = {'a': {0: True, 1: True}, 'b': {0: False, 1: False}, 'c': {0: True, 1: False}}
df = pd.DataFrame(data=data)
Код:
df["output"] = (pd
.melt(frame=df.reset_index(), id_vars=["index"])
.query(expr = "value.eq(True)")
.groupby(by = "index")
.variable.apply(func=list)
)
print(df)
Результат:
a b c output
0 True False True [a, c]
1 True False False [a]
Вы можете использовать stack и groupby:
df["output"] = df[df].stack().reset_index().groupby("level_0")["level_1"].agg(list)
a b c output
0 True False True [a, c]
1 True False False [a]
Код
1. Если у вас небольшие данные, проще всего использовать apply.
df['output'] = df.apply(lambda x: x.index[x].tolist(), axis=1)
2. Если ваши данные большие, используйте библиотеку numpy.
arr1 = df.columns.to_numpy()
df['output'] = [arr1[row].tolist() for row in df.to_numpy()]
Даже если это цикл, с numpy это происходит быстрее.
Ого, не знала о плавлении, это так чисто - спасибо!