Вопрос или проблема
Я пытаюсь сравнить значения адресов на предмет неточностей, например, данные по нескольким записям, как показано ниже:
Ссылка | Квартира | Адрес | Почтовый индекс |
---|---|---|---|
AS097 | NaN | 00 Name Road | BH1 4HB |
AS097 | Квартира 1 Название здания | 00 Name Road | BH1 4HB |
AS097 | Квартира 2 Название здания | 00 Name Rd | BH1 4HB |
AS097 | Квартира 3 Название здания | 00 Name Road | BH1 4HB |
AS097 | Квартира 4 Название здания | 00 Name Road | BH1 4HB |
AS097 | Квартира 5 Название здания | 00 Name Road | BH1 4HX |
HO056 | NaN | 23 Street Road | XG9 9GX |
У меня есть фрейм данных, где я сохраняю все “основные” адреса, проверяя, пуст ли столбец Квартира:
main_address = df['Apartment'].isnull()
df_st = pd.DataFrame({'Reference':df[main_address].Reference, 'Address':df[main_address].Address, 'PostCode':df[main_address].PostCode})
df_st
будет выглядеть так:
Ссылка | Квартира | Адрес | Почтовый индекс |
---|---|---|---|
AS097 | NaN | 00 Name Road | BH1 4HB |
HO056 | NaN | 23 Street Road | XG9 9GX |
df
содержит более 1K записей, но df_st
, содержащий “основной” адрес, заканчивается примерно на 200 записях.
Я пытаюсь создать новый DataFrame, где смогу определить, где записи не совпадают, сравнивая df
с df_st
.
ПРОБЛЕМА
Я пробую следующее:
# Очистить значения ссылок
refs_list = df['Reference'].str.split("https://datascience.stackexchange.com/").str[0]
df['Reference'] = refs_list
# Создать новый столбец с названием issues и отметить, если ссылки совпадают
df['issues'] = np.where(df['Reference'] == df_st['Reference'], 'True', 'False')
Я хочу сделать то же самое для Address
и PostCode
, но, к сожалению, это не сработало, так как df
и df_st
не имеют одинаковой формы.
Мне сложно найти способ достичь сравнения между двумя DataFrame df
и df_st
.
Я хочу сравнить все совпадающие значения строк Reference
из df
с соответствующими значениями из df_st
и, если они не совпадают, создать новый столбец с названием Issues
и сохранить там конфликтующие столбцы.
МОЙ ЖЕЛАЕМЫЙ РЕЗУЛЬТАТ
Учитывая вышеприведенные данные, после сравнения данных df
с df_st
получается новый DataFrame, как ниже
Ссылка | Квартира | Адрес | Почтовый индекс | Проблемы |
---|---|---|---|---|
AS097 | NaN | 00 Name Road | BH1 4HB | Нет |
AS097 | Квартира 1 Название здания | 00 Name Road | BH1 4HB | Нет |
AS097 | Квартира 2 Название здания | 00 Name Rd | BH1 4HB | Адрес |
AS097 | Квартира 3 Название здания | 00 Name Road | BH1 4HB | Нет |
AS097 | Квартира 4 Название здания | 00 Name Road | BH1 4HB | Нет |
AS097 | Квартира 5 Название здания | 00 Name Road | BH1 4HX | Почтовый индекс |
HO056 | NaN | 23 Street Road | XG9 9GX | Нет |
Где Address
появляется как проблема в столбце Issues
, так как адреса не совпадают с df_st
, так же для PostCode
, так как он отличается от df_st
В РЕЗЮМЕ
Все, что я хочу знать, это как сравнивать совпадающие строки по Reference
из одного DataFrame с другим и сравнивать другие значения Address
и PostCode
.
Надеюсь, это имеет смысл.
Вы можете объединить df
и df_st
по Reference
:
df_merged = pd.merge(df, df_st, on="Reference", how="left")
Примечание: how="left"
действительно зависит от того, что вы хотите в объединенной таблице. Затем вы можете сравнить значения в объединенных столбцах:
df_merged['Address_df'] == df_merged['Address_df_st']
Ответ или решение
Для эффективного сравнения значений адресов из одного DataFrame с одной строкой из другого DataFrame, вы можете использовать метод объединения в Pandas, который позволяет сопоставить строки на основе определенного критерия, в вашем случае — значения в столбце Reference
. После этого осуществить сравнение нужных вам столбцов.
Для начала, давайте определим ваши исходные данные. У вас есть DataFrame, в который хотите внести коррективы, основываясь на данных из DataFrame с основными адресами. Давайте представим, что ваши DataFrame обозначены как df
и df_st
.
Шаги по выполнению задачи
-
Объединение DataFrame (Merge):
Используйтеpd.merge()
для объединенияdf
иdf_st
по столбцуReference
. Это создаст новый DataFrame, в котором будут содержаться все строки изdf
вместе с соответствующими основными адресами изdf_st
.import pandas as pd df_merged = pd.merge(df, df_st, on='Reference', suffixes=('', '_main'), how='left')
В данном случае добавляется суффикс
_main
к столбцам изdf_st
, чтобы избежать путаницы при сравнении. -
Сравнение значений:
Затем, вам необходимо сравнить значенияAddress
иPostCode
в объединённом DataFrame, и создать новый столбецIssues
, который будет содержать информацию о том, в каких столбцах есть несоответствия.def identify_issues(row): issues = [] if row['Address'] != row['Address_main']: issues.append('Address') if row['PostCode'] != row['PostCode_main']: issues.append('PostCode') return ', '.join(issues) if issues else 'None' df_merged['Issues'] = df_merged.apply(identify_issues, axis=1)
-
Формирование результирующего DataFrame:
Полученный DataFramedf_merged
будет включать информацию о расхождениях, и будет иметь следующую структуру:result = df_merged[['Reference', 'Apartment', 'Address', 'PostCode', 'Issues']]
Пример полного кода
Соберем все в одно целое для наглядности:
import pandas as pd
import numpy as np
# Исходные данные
data = {
'Reference': ['AS097', 'AS097', 'AS097', 'AS097', 'AS097', 'AS097', 'HO056'],
'Apartment': [np.nan, 'Flat 1 Building Name', 'Flat 2 Building Name',
'Flat 3 Building Name', 'Flat 4 Building Name',
'Flat 5 Building Name', np.nan],
'Address': ['00 Name Road', '00 Name Road', '00 Name Rd',
'00 Name Road', '00 Name Road', '00 Name Road', '23 Street Road'],
'PostCode': ['BH1 4HB', 'BH1 4HB', 'BH1 4HB', 'BH1 4HB',
'BH1 4HB', 'BH1 4HX', 'XG9 9GX']
}
data_st = {
'Reference': ['AS097', 'HO056'],
'Address': ['00 Name Road', '23 Street Road'],
'PostCode': ['BH1 4HB', 'XG9 9GX']
}
df = pd.DataFrame(data)
df_st = pd.DataFrame(data_st)
# Объединяем DataFrame
df_merged = pd.merge(df, df_st, on='Reference', suffixes=('', '_main'), how='left')
# Определяем несоответствия
def identify_issues(row):
issues = []
if row['Address'] != row['Address_main']:
issues.append('Address')
if row['PostCode'] != row['PostCode_main']:
issues.append('PostCode')
return ', '.join(issues) if issues else 'None'
df_merged['Issues'] = df_merged.apply(identify_issues, axis=1)
# Получаем результирующий DataFrame
result = df_merged[['Reference', 'Apartment', 'Address', 'PostCode', 'Issues']]
print(result)
Заключение
Данный подход позволяет вам гибко сопоставлять значения адресов и почтовых индексов, а также быстро выявлять несоответствия между различными записями. Этот метод станет особенно полезным при выполнении дальнейшего анализа данных и очистки, поскольку позволяет легко определить проблемные области для устранения ошибок.