Выполнение pandas объединения с несколькими значениями слева и одним справа - PullRequest
0 голосов
/ 19 февраля 2020

Мне нужна помощь для объединения двух наборов данных в pandas.

Мой первый набор данных - это набор данных контактов, включая имя и идентификатор. Второй - это набор данных сделок, который среди других полей включает один столбец с несколькими идентификаторами контактов, разделенными запятыми. Я хотел бы присоединить набор данных сделок к набору данных контактов, где идентификатор контакта совпадает с одним из идентификаторов в поле «связанные контакты».

contacts_df = pd.DataFrame(
  {'name': ['John Smith', 'Jane Doe', 'James Bond'],
  'id': [1,2,3]}
  

deals_df = pd.DataFrame(
  {'deal_name': ['McDonalds', 'KFC'],
  'associated_contacts':['1,3','2']}

Я разбил контакты в кадре данных сделок на четыре разных столбца:

deals_df[['Contact ID 1','Contact ID 2','Contact ID 3', 'Contact ID 4']] = deals_df['associated_contacts'].str.split(',',expand=True)

И попытался присоединить это к набору данных контактов:

merged = contacts_df.merge(deals_df, how='left', left_on='id', 
                    right_on=['Contact ID 1','Contact ID 2','Contact ID 3','Contact ID 4'])

Но это вернуло ValueError:

ValueError: len(right_on) must equal len(left_on)

Может Кто-нибудь, помогите мне присоединиться к этим двум наборам данных, пожалуйста? Я думаю, что в моем наборе данных каждый контакт будет связан только с одной сделкой. Но сделка может иметь несколько контактов, и я хотел бы видеть сделку, связанную с каждым.

1 Ответ

0 голосов
/ 19 февраля 2020

Используйте DataFrame.explode (pandas 0.25+) для повторяющихся значений associated_contacts, разделенных на ,, laso необходимо преобразовать столбец id в целые числа:

deals_df = (deals_df.assign(id = deals_df.pop('associated_contacts').str.split(','))
                    .explode('id')
                    .assign(id = lambda x: x['id'].astype(int)))
print (deals_df)
   deal_name  id
0  McDonalds   1
0  McDonalds   3
1        KFC   2

Ваше решение должно быть изменено с DataFrame.stack и DataFrame.join на оригинал:

deals_df = (deals_df.join(deals_df.pop('associated_contacts')
                                  .str.split(',', expand=True)
                                  .stack()
                                  .astype(int)
                                  .reset_index(level=1, drop=True)
                                  .rename('id')))
print (deals_df)
0  McDonalds   1
0  McDonalds   3
1        KFC   2

А затем используйте merge с параметром on только:

merged = contacts_df.merge(deals_df, how='left', on='id')
print (merged)
         name  id  deal_name
0  John Smith   1  McDonalds
1    Jane Doe   2        KFC
2  James Bond   3  McDonalds
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...