Как мне извлечь строки из другого фрейма данных на основе ограничения datetime?

#python-3.x #pandas #numpy #dataframe #jupyter-notebook

#python-3.x #pandas #numpy #фрейм данных #jupyter-notebook

Вопрос:

По сути, я пытаюсь ответить на вопрос: «Каковы самые последние 4 заказа клиентов с даты X …» но проблема в том, что я пытаюсь сделать это для каждой строки в таблице, упорядоченной по журналам электронной почты и имеющей уникальную дату.

Поэтому мне пришлось бы просмотреть каждую дату в этих журналах электронной почты (df1), выяснить, совпадает ли идентификатор агента в df1 с идентификатором агента df2 (история заказов), а затем извлечь самые последние 4 заказа из df2. Т.Е. Клиент 123 получает электронное письмо 3 марта (df1)… Затем мне нужно будет извлечь 4 самые последние записи клиента 123 в df2, которые равны или меньше даты (3 марта).

Я придумал эту грязную функцию, но она не очень практична при циклическом переборе 1000 строк… Есть идеи по расширению этого?

Спасибо,

 df1 = pd.DataFrame({'unique_col': ['a', 'b', 'c', 'd'], 'agent_id': [1, 2, 3, 4], 'created_at_email': ['1/5/2020', '1/6/2020', '1/8/2020', '1/8/2020']})
df2 = pd.DataFrame({'unique_col': ['a', 'b', 'c', 'd'], 'agent_id': [1, 1, 3, 1], 'created_at': ['1/4/2020', '1/5/2020', '1/6/2020', '1/9/2020']})

# note: super not optimized at all...
def function():
    for index, row in df1.iterrows():
        for index, row2 in df2.iterrows():
            if row['agent_id'] == row2['agent_id']:
                if row2['created_at'] <= row['created_at_email']:
                    print( 1, row2['created_at'], row['created_at_email'], row2['agent_id'], row['agent_id'], row['unique_col'], row2['unique_col'])
                else:
                    print( 0, row2['created_at'], row['created_at_email'], row2['agent_id'], row['agent_id'], row['unique_col'], row2['unique_col'])
            #else:
                #print( 0, row2['created_at'], row['created_at_email'], row2['agent_id'], row['agent_id'])
                    
                    
            
function()
 
 output:
1 1/4/2020 1/5/2020 1 1 a a
1 1/5/2020 1/5/2020 1 1 a b
0 1/9/2020 1/5/2020 1 1 a d
1 1/6/2020 1/8/2020 3 3 c c 
 

Ответ №1:

Во-первых, нам нужно установить соответствие между df1 и df2 для извлечения created_at_email

Для этого вы можете установить оба индекса agent_id фреймов данных в качестве столбца, после этого мы можем объединить оба фрейма данных

 df1.index = df1.agent_id
df2.index = df2.agent_id
result = df2.join(df1,lsuffix='_df2')
 

join Метод совпадения основан на равенстве индекса.

Мы сбросим индекс result , чтобы предотвратить ошибки во groupby время, а также удалим ненужные столбцы

 result.reset_index(drop=True,inplace=True)
result.drop(['agent_id_df2'],axis=1,inplace=True)
 

Чтобы сохранить самые последние заказы каждого agent_id , мы отсортируем фрейм данных по created_at и agent_id

 result.sort_values(['agent_id','created_at'],inplace=True)
 

После этого вы можете выполнить a groupby с head помощью метода для извлечения 4 последних заказов каждого агента

 result = result.groupby('agent_id').head(4)
 

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

unique_col_df2 created_at unique_col agent_id created_at_email
0 a 1/4/2020 a 1 1/5/2020
1 b 1/5/2020 a 1 1/5/2020
2 d 1/9/2020 a 1 1/5/2020
3 c 1/6/2020 c 3 1/8/2020

Комментарии:

1. Эй, спасибо за ответ! Я думаю, мне следовало уточнить… «Итак, мне нужно было бы просмотреть каждую дату в этих журналах электронной почты (df1), выяснить, совпадает ли идентификатор агента в df1 с идентификатором агента df2 (история заказов), а затем извлечь самые последние 4 заказа из df2 РЕДАКТИРОВАТЬ: с даты в df1. Т.Е. Если клиент 123 вdf1 получил электронное письмо 3 марта. Мне нужно было бы заглянуть в журналы заказов (df2) и получить 4 самые последние записи (строки) с этой даты в df1 (3 марта). Клиент 123 может появляться в df1 несколько раз, уникальным разделителем является дата. Спасибо!