#apache-spark #pyspark #apache-spark-sql #pyspark-dataframes
#apache-spark #apache-spark-sql #pyspark
Вопрос:
У меня есть 2 таблицы, как показано ниже. Мой приведенный ниже код объединяет 2 таблицы (левое соединение). Проблема в том, что я должен выполнить одно и то же соединение дважды. Первое объединение выполняется для log_no и LogNumber, которое возвращает все записи из левой таблицы (table1) и соответствующие записи из правой таблицы (table2). Второе соединение выполняет то же самое, но в подстроке log_no с LogNumber . например, 777 будет совпадать с 777 из таблицы 2, 777-A совпадения нет, но при использовании функции подстроки 777-A становится 777, который будет сопоставлен в таблице 2.
Вместо создания 2 отдельных объединений, как показано ниже, как я могу охватить оба сценария одним объединением. Код ниже:
# first join to match 1234-A (table 1) with 1234-A (table 2)
df5 = df5.join(df_app, trim(df5.LOG_NO) == trim(df_app.LogNumber), "left")
.select (df5["*"], df_app["ApplicationId"])
df5 = df5.withColumnRenamed("ApplicationId","ApplicationId_1")
# second join with substring function, to match 777-C with 777,
# my string is longer than my examples, this is why I have a substring for the first 8 characters. I provided simple examples.
df5 = df5.join(df_app, substring(trim(df5.LOG_NO), 1, 8) == trim(df_app.LogNumber), "left")
.select (df5["*"], df_app["ApplicationId"])
df5 = df5.withColumnRenamed("ApplicationId","ApplicationId_2")
Ответ №1:
Вы можете объединить два условия соединения, используя побитовое ИЛИ:
df5 = df5.join(df_app,
(trim(df5.LOG_NO) == trim(df_app.LogNumber)) |
(substring(trim(df5.LOG_NO), 1, 8) == trim(df_app.LogNumber)),
"left")
.select(df5["*"], df_app["ApplicationId"])
Комментарии:
1. Я в замешательстве, почему И? это означает, что оба условия должны быть истинными. Если первое условие не выполняется, то условие подстроки должно быть истинным.
2. @AJR Извините, должно быть ИЛИ. Отредактировал мой ответ.
3. Моя программа не завершается…. Мне пришлось убить его после удвоения времени. Обычно моя работа по склеиванию занимает около 22 минут, я дал ей поработать 44 минуты, и она все еще работала… По какой-то причине я думаю, что побитовое ИЛИ помещает мою программу в цикл, и она не завершается. Любой другой совет?? Спасибо
4. @AJR Сначала попробуйте использовать меньший фрейм данных, чтобы убедиться, что он выполняет работу правильно. Нет никакого способа, чтобы «ИЛИ» поместило вашу программу в цикл. Это просто невозможно.