#python #pandas #dataframe
Вопрос:
У меня есть фрейм данных, в котором хранится, где живет человек, и он выглядит примерно так:
РАЗДЕЛ | подушечка | комната | человек |
---|---|---|---|
1 | A | 101 | ПЕРСОНА1 |
1 | A | 102 | ПЕРСОНА 2 |
1 | B | 101 | ПЕРСОНА 3 |
2 | A | 103 | ПЕРСОНА4 |
2 | C | 102 | ПЕРСОНА 5 |
У меня также есть другой фрейм данных, в котором указаны все комбинации СЕКТ/ПЛОЩАДОК/КОМНАТ, которые делают эту жилую единицу особенной (примечание: если не существует start_room и end_room, это означает, что все комнаты в этой секте/площадке являются особенными):
РАЗДЕЛ | подушечка | комната | START_ROOM | КОНЕЦ КОМНАТЫ |
---|---|---|---|---|
1 | A | 101 | 100 | 104 |
1 | A | 102 | ||
1 | C | 101 | 105 | 500 |
Есть ли способ идентифицировать все жилые единицы, которые являются «особыми», с помощью «специального» фрейма данных, а затем добавить новый столбец в первый фрейм данных, помечающий их. «Специальный» фрейм данных намного больше, и если бы мне пришлось вручную выполнить условное условие .заявление о местонахождении, чтобы идентифицировать все специальные жилые единицы, заняло бы целую вечность. Я хотел бы иметь возможность просто сопоставлять их программно
Комментарии:
1. Пожалуйста, укажите ваши ожидаемые результаты.
2. В принципе, я ищу всех людей в первой таблице, которые соответствуют одному из критериев из второй таблицы. Результатом будет df с ЧЕЛОВЕКОМ 1 и ЧЕЛОВЕКОМ 2.
3. Но для РАЗДЕЛА 1 PAD A у вас есть 2 строки во втором кадре данных. Итак, только от 100 до 104 специальных номеров или все номера специальные?
Ответ №1:
Поэтому я бы объединил первый фрейм данных в специальный фрейм данных, а затем добавил столбец со специальным условием
df_person = pd.DataFrame({'SECT': [1, 1, 1, 2, 2],
'PAD': ['A', 'A', 'B', 'A', 'C'],
'ROOM': [101, 102, 101, 103, 102],
'PERSON': ['PERSON1', 'PERSON2', 'PERSON3', 'PERSON4', 'PERSON5']})
df_special = pd.DataFrame({'SECT':[1, 1, 1],
'PAD':['A', 'A', 'C'],
'ROOM':[101, 102, 101],
'START_ROOM': [100, '', 105],
'END_ROOM': [104, '', 500]})
df_merged = df_person.merge(df_special, on=['SECT', 'PAD', 'ROOM'], how='left')
rows_to_update1 = df_merged[(df_merged['START_ROOM']=='')amp;
(df_merged['END_ROOM']=='')].index
rows_to_update2 = df_merged[((df_merged['ROOM'].astype('int32')>=pd.to_numeric(df_merged['START_ROOM'], errors='coerce'))amp;
(df_merged['ROOM'].astype('int32')<=pd.to_numeric(df_merged['END_ROOM'], errors='coerce')))].index
df_merged['IS_SPECIAL'] = False
df_merged.loc[rows_to_update1.union(rows_to_update2), 'IS_SPECIAL'] = True
Это сложная проблема, хотя в том, что ваши START_ROOM и END_ROOM представляют собой смесь строк и целых чисел. Я бы предложил не использовать эти две колонки в качестве пустых строк, чтобы обозначить, что все комнаты являются особенными.
Ответ №2:
Поскольку пустые строки подразумевают, что все комнаты являются особыми, вы можете просто заполнить их фиктивными значениями (минимальными и максимальными из первого df), а затем получить требуемый результат из объединенного кадра данных.
Предполагая , что ваши фреймы данных являются df1
и df2
, вы могли бы сделать:
df2["START_ROOM"] = df2["START_ROOM"].fillna(df1["ROOM"].min())
df2["END_ROOM"] = df2["START_ROOM"].fillna(df1["ROOM"].max())
merged = df1.merge(df2, on=["SECT", "PAD", "ROOM"], how="left")
result = df1[df1["PERSON"].isin(merged.dropna()["PERSON"].tolist())]
>>> result
SECT PAD ROOM PERSON
0 1 A 101 PERSON1
1 1 A 102 PERSON2