добавление значений в pandas столбцы фрейма данных на основе другого фрейма данных - PullRequest
1 голос
/ 28 мая 2020

У меня есть фрейм данных, который выглядит так (df):

HOUSEID    PERSONID      WHY_TRP
20000017      1            1
20000017      1            1
20000017      1            1
20000017      2            1
20000017      2            3
20000231      1            11
20000231      1            11
20000231      2            11
20000521      1            11
20000521      2            11
20000521      2            3

Каждая строка описывает поездку, совершенную человеком. У меня есть другой фрейм данных того же типа, в котором каждая строка описывает человека (df_p):

    HOUSEID   PERSONID   
    20000017      1      
    20000017      2     
    20000231      1    
    20000231      2    
    20000521      1    
    20000521      2 

Я хочу создать три новых столбца во втором фрейме данных, чтобы показать частоту 1, 3 и 11 для каждый человек. в основном у меня уже есть второй фрейм данных (df_p) с другими функциями, поэтому мне не следует использовать groupby. по какой-то причине в первом и втором фреймах данных разное количество людей. вот почему мне понадобилась стратегия ниже. Это код, который я пробовал, но на его выполнение потребовалось несколько часов (1 миллион итераций):

df_p.insert(2, 'WHY_TRP_1', 0)
df_p.insert(3, 'WHY_TRP_2', 0)
df_p.insert(4, 'WHY_TRP_3', 0)

def trip_counter(i, r):
  if r[2] == 1:
    df_p.loc[(df_p['HOUSEID'] == r[0]) & (df_p['PERSONID'] == r[1]), ['WHY_TRP_1']] += 1 
  elif r[2] == 3:
    df_p.loc[(df_p['HOUSEID'] == r[0]) & (df_p['PERSONID'] ==  r[1]), ['WHY_TRP_3']] += 1 
  elif r[2] == 11:
    df_p.loc[(df_p['HOUSEID'] == r[0]) & (df_p['PERSONID'] ==  r[1]), ['WHY_TRP_11']] += 1


for i ,r in df.iterrows():
  trip_counter(i ,r) 

вывод:

     HOUSEID   PERSONID   WHY_TRP_1     WHY_TRP_3      WHY_TRP_11
    20000017      1            3            0            0
    20000017      2            1            1            0
    20000231      1            0            0            2
    20000231      2            0            0            1
    20000521      1            0            0            1
    20000521      2            0            1            1          

Есть ли более быстрый способ сделать это?

спасибо

Ответы [ 2 ]

1 голос
/ 28 мая 2020

Вы также можете сделать pivot_table, а затем merge:

m = df.pivot_table(index=['HOUSEID','PERSONID'],
                   columns='WHY_TRP',aggfunc=len,fill_value=0)

out= df_p.merge(m.add_prefix('WHY_TRP'),left_on=['HOUSEID','PERSONID'],right_index=True)

print(out)

    HOUSEID  PERSONID  WHY_TRP1  WHY_TRP3  WHY_TRP11
0  20000017         1         3         0          0
1  20000017         2         1         1          0
2  20000231         1         0         0          2
3  20000231         2         0         0          1
4  20000521         1         0         0          1
5  20000521         2         0         1          1
1 голос
/ 28 мая 2020

Вы можете получить таблицу подсчетов, выполнив groupby на первом фрейме данных и распаковав WHY_TRP, а затем вы можете просто объединить его со вторым:

counts = df.groupby(["HOUSEID", "PERSONID", "WHY_TRP"]).apply(len).unstack(fill_value=0)

counts.columns = counts.columns.map(lambda x: f"WHY_TRP_{x}")

counts

WHY_TRP            WHY_TRP_1  WHY_TRP_3  WHY_TRP_11
HOUSEID  PERSONID
20000017 1                 3          0           0
         2                 1          1           0
20000231 1                 0          0           2
         2                 0          0           1
20000521 1                 0          0           1
         2                 0          1           1

df2.merge(counts, how="left", left_on=["HOUSEID", "PERSONID"], right_index=True)

    HOUSEID  PERSONID  WHY_TRP_1  WHY_TRP_3  WHY_TRP_11
0  20000017         1          3          0           0
1  20000017         2          1          1           0
2  20000231         1          0          0           2
3  20000231         2          0          0           1
4  20000521         1          0          0           1
5  20000521         2          0          1           1
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...