Перебирать столбцы pandas и добавлять dict наборов?

#python #pandas #dictionary #set

#python #pandas #словарь #набор

Вопрос:

Я хочу перебрать около 10 миллионов строк в фрейме данных pandas и добавить их к уже существующему dict наборов.

Например, для такого dict

 x = {10: {1, 2, 3, 5}, 12: {6, 7, 8, 9, 10}}
 

И фрейм данных, подобный этому:

 d = {'ID': [10, 10, 10, 12, 12, 12], 'Another_ID': [1, 4, 6, 6, 7, 13]}
df = pd.DataFrame(data=d)

ID   Another_ID

10   1
10   4
10   6
12   6
12   7
12   13
 

Я хотел бы просмотреть строки и добавить новые значения, которые ID «еще не видел». Я хотел бы получить такой результат.

 x = {10: {1, 2, 3, 4, 5, 6}, 12: {6, 7, 8, 9, 10, 13}}
 

Я попытался выполнить итерацию с помощью простой функции, подобной следующей.

 for i in df [['ID' , 'Another_ID' ]] .values():
    dict[i[0]].add(i[1])
 

Я могу вручную добавить значения, сказав следующее, как это, но не могу сделать это в цикле!

   dict[10].add(6)
 

Если кто-нибудь знает, как перебирать эти два столбца pandas и добавлять новые значения в набор, пожалуйста, дайте мне знать!

  • имейте в виду, что это должно быть сделано относительно быстро, так как имеется 10 миллионов строк

Спасибо!

Ответ №1:

Вы можете преобразовать df в формат, аналогичный «x», используя groupby и agg :

 x2 = df.groupby('ID')['Another_ID'].agg(set).to_dict()
print (x2)
# {10: {1, 4, 6}, 12: {6, 7, 13}}
 

Теперь мы объединяем два словаря, используя одно выражение:

 x3 = {k: x.get(k, set()) | x2.get(k, set()) for k in x}
print (x3)
# {10: {1, 2, 3, 4, 5, 6}, 12: {6, 7, 8, 9, 10, 13}}
 

Или, для слияния на месте (имеет больше смысла, если x велико и x2 мало):

 for k in x2:
    x[k] = x2[k] | x.get(k, set())

print (x)
# {10: {1, 2, 3, 4, 5, 6}, 12: {6, 7, 8, 9, 10, 13}}
 

Где | оператор представляет собой заданное объединение двух заданных операндов.

Ответ №2:

Один путь от панды explode

 out = pd.Series(x).map(list).explode().append(df.set_index('ID')['Another_ID']).groupby(level=0).agg(set).to_dict()
Out[361]: {10: {1, 2, 3, 4, 5, 6}, 12: {6, 7, 8, 9, 10, 13}}
 

Ответ №3:

Вы можете обрабатывать свой фрейм данных как словарь, использовать defaultdict для извлечения ваших данных из фрейма данных Pandas, а затем выполнять итерации по словарю, чтобы получить конечный результат:

 from collections import defaultdict

dd = defaultdict(list)

for ID, another_ID in zip(df.ID, df.Another_ID):
    dd[ID].append(another_ID)

dd

defaultdict(list, {10: [1, 4, 6], 12: [6, 7, 13]})
 

Конечный результат:

 {key: value.union(dd[key]) for key, value in x.items()}

{10: {1, 2, 3, 4, 5, 6}, 12: {6, 7, 8, 9, 10, 13}}