Pandas – Map – Dummy Variables – присвоить значение 1

У меня есть два кадра данных, x.head() выглядит так:

top      mid       adc      support jungle
Irelia   Ahri      Jinx     Janna   RekSai
Gnar     Ahri      Caitlyn  Leona   Rengar
Renekton Fizz      Sivir    Annie   Rengar
Irelia   Leblanc   Sivir    Thresh  JarvanIV
Gnar     Lissandra Tristana Janna   JarvanIV

и фрейм данных fullmatrix.head(), который я создал, выглядит так:

Irelia  Gnar    Renekton    Kassadin    Sion    Jax Lulu    Maokai  Rumble  Lissandra   ... XinZhao Amumu   Udyr    Ivern   Shaco   Skarner FiddleSticks    Aatrox  Volibear    MonkeyKing
0   0   0   0   0   0   0   0   0   0   0   ... 0   0   0   0   0   0   0   0   0   0
1   0   0   0   0   0   0   0   0   0   0   ... 0   0   0   0   0   0   0   0   0   0
2   0   0   0   0   0   0   0   0   0   0   ... 0   0   0   0   0   0   0   0   0   0
3   0   0   0   0   0   0   0   0   0   0   ... 0   0   0   0   0   0   0   0   0   0
4   0   0   0   0   0   0   0   0   0   0   ...

Теперь я не могу понять, как присвоить значение 1 для каждого имени в фрейме данных x соответствующему столбцу с тем же именем в фрейме данных fullmatrix построчно (оба фрейма данных имеют одинаковое количество строк).


person bloo    schedule 24.12.2017    source источник
comment
бросьте нам кость здесь. упростите этот образец набора данных примерно до 1/10 того, что у вас есть здесь, и включите ожидаемый результат (даже если вам придется рассчитывать его вручную).   -  person Paul H    schedule 25.12.2017
comment
Извините, Пол, вывод должен выглядеть как второй кадр данных только с 1, где имя появляется под столбцом для соответствующей строки. Также я все еще пытаюсь понять, как правильно отображать мои таблицы. Ирелия Гнар Ари Ренектон Джинкс Кассадин Жанна Сион РекСай 1 0 1 0 1 0 1 0 1   -  person bloo    schedule 25.12.2017


Ответы (3)


Я уверен, что это можно улучшить, но одно преимущество заключается в том, что для этого требуется только первый DataFrame, и концептуально приятно объединять операции в цепочку, пока вы не получите желаемое решение.

fullmatrix = (x.stack()
               .reset_index(name='names')
               .pivot(index='level_0', columns='names', values='names')
               .applymap(lambda x: int(x!=None))
               .reset_index(drop=True))

обратите внимание, что только имена, которые появляются в вашем x DataFrame, будут отображаться как столбцы в fullmatrix. если вам нужны дополнительные столбцы, вы можете просто выполнить соединение.

person Seiji Armstrong    schedule 24.12.2017
comment
Я получаю: ValueError: Индекс содержит повторяющиеся записи, не может изменить форму. Это работает, если я удалю index='level_0'. Проверка правильности присвоения значений. - person bloo; 25.12.2017
comment
Из вашего сообщения неясно, что x имеет в качестве индекса, поскольку я предполагаю, что вы только что напечатали столбцы. Не могли бы вы либо напечатать свой индекс, либо сначала включить reset_index(drop=True). Так это будет выглядеть x.reset_index(drop=True).stack()..... - person Seiji Armstrong; 25.12.2017
comment
Легенда. Просто быстро протестировано, и он присваивает значения так, как должен. Спасибо за быстрый ответ. - person bloo; 25.12.2017
comment
Потрясающий. И последнее, что касается проблемы индекса... если ваш индекс также содержит имена, которые вы хотите подсчитать (например, если ваш столбец top на самом деле является индексом), вы можете установить drop=False в первом reset_index, а затем он появится в DataFrame при стеке это, а затем появиться в кадре окончательного подсчета. - person Seiji Armstrong; 25.12.2017

Рассмотрите возможность добавления столбца key = 1, а затем итерации по каждому столбцу для получения списка сводных поисковых файлов, которые вы затем горизонтально объединяете с pd.concat. Наконец, запустите DataFrame.update(), чтобы обновить исходный < em>fullmatrix со значениями из pvt_df, выровненными по индексам.

x['key'] = 1

dfs = []
for col in x.columns[:-1]:
    dfs.append(x.pivot_table(index=df.index, columns=[col], values='key').fillna(0))

pvt_df = pd.concat(dfs, axis=1).astype(int)

fullmatrix.update(pvt_df)
fullmatrix = fullmatrix.astype(int)

fullmatrix   # ONLY FOR VISIBLE COLUMNS IN ORIGINAL POST
#    Irelia  Gnar  Renekton  Kassadin  Sion  Jax  Lulu  Maokai  Rumble  Lissandra  XinZhao  Amumu  Udyr  Ivern  Shaco  Skarner  FiddleSticks  Aatrox  Volibear  MonkeyKing
# 0       1     0         0         0     0    0     0       0       0          0        0      0     0      0      0        0             0       0         0           0
# 1       0     1         0         0     0    0     0       0       0          0        0      0     0      0      0        0             0       0         0           0
# 2       0     0         1         0     0    0     0       0       0          0        0      0     0      0      0        0             0       0         0           0
# 3       1     0         0         0     0    0     0       0       0          0        0      0     0      0      0        0             0       0         0           0
person Parfait    schedule 24.12.2017
comment
Я получаю ValueError: невозможно переиндексировать повторяющуюся ось в fullmatrix.update(pvt_df), индекс в (index=df.index, columns=[col], values='key') должен быть =dfs.index или что-то другое? - person bloo; 25.12.2017

OP пытается создать таблицу фиктивных переменных с набором точек данных. Для каждой точки данных он содержит 5 атрибутов. Всего имеется N уникальных атрибутов.

Мы будем использовать упрощенный набор данных, чтобы продемонстрировать, как это сделать:

  • 5 уникальных атрибутов
  • 3 записи данных
  • каждая запись данных содержит 3 атрибута.

    x = pd.DataFrame([['a', 'b', 'c'],  
                      ['b', 'd', 'e'], 
                      ['e', 'b', 'a']])
    fullmatrix = pd.DataFrame([[0 for _ in range(5)] for _ in range(3)], 
                              columns=['a','b','c','d','e'])
    """ fullmatrix:
       a  b  c  d  e
    0  0  0  0  0  0
    1  0  0  0  0  0
    2  0  0  0  0  0
    """
    
    # each row in x_temp is a string of attributed delimited by ","
    x_row_joined = pd.Series((",".join(row[1]) for row in x.iterrows()))    
    fullmatrix = x_row_joined.str.get_dummies(sep=',')
    

Метод вдохновлен offbyone ответ Он использует pandas.Series.str.get_dummies. Сначала мы соединяем каждую строку x с указанным разделителем. Затем используйте метод Series.str.get_dummies. Метод принимает разделитель, который мы просто используем для объединения атрибутов, и создаст для вас таблицу фиктивных переменных. (Внимание: не выбирайте sep, существующее в x.)

person Tai    schedule 24.12.2017
comment
Я попробовал первое решение, и я получаю вывод, который выглядит так, как он должен быть, но 1 не в том месте. - person bloo; 25.12.2017
comment
Может быть, ваш columns имеет другой порядок? @bloo Попробуйте проверить порядок столбцов в fullmatrix. - person Tai; 25.12.2017
comment
Я пытаюсь отладить проблему через свой блокнот Jupyter, и я собираюсь ответить, работает ли это. Я хочу использовать ваше первое решение, потому что оно простое, имеет смысл, и другие люди могут читать и понимать, что происходит. - person bloo; 25.12.2017
comment
@bloo Пытался просто ответить. Надеюсь это поможет. Счастливого Рождества. - person Tai; 25.12.2017