как слить два ряда в искру? - PullRequest
1 голос
/ 05 апреля 2020

Мне нужно объединить строки в одном и том же кадре данных на основе ключевого столбца «id». В примере фрейма данных 1 строка содержит данные для идентификатора, имени и возраста. У другой строки есть идентификатор, имя и зарплата. Строки с одинаковым ключом 'id' должны быть объединены в одну запись в конечном кадре данных. Если есть только одна запись, следует показать их также с нулевыми значениями [Смит и Джейк], как в примере ниже.

Вычисления должны выполняться на данных в реальном времени, идеальным решением на основе искровых функций. Я попытался отфильтровать записи, основанные на столбцах возраста и города, чтобы разделить фреймы данных, и они выполняют левое соединение по идентификатору. Но это не очень эффективно. Ищете любые альтернативные предложения. Заранее спасибо!

Пример кадра данных

val inputDF= Seq(("100","John", Some(35),None)
,("100","John", None,Some("Georgia")),
("101","Mike", Some(25),None),
("101","Mike", None,Some("New York")),
("103","Mary", Some(22),None),
("103","Mary", None,Some("Texas")),
("104","Smith", Some(25),None),
("105","Jake", None,Some("Florida")))
.toDF("id","name","age","city")

Входной кадр данных

+---+-----+----+--------+
|id |name |age |city    |
+---+-----+----+--------+
|100|John |35  |null    |
|100|John |null|Georgia |
|101|Mike |25  |null    |
|101|Mike |null|New York|
|103|Mary |22  |null    |
|103|Mary |null|Texas   |
|104|Smith|25  |null    |
|105|Jake |null|Florida |
+---+-----+----+--------+ 

Ожидаемый выходной кадр данных

+---+-----+----+---------+
| id| name| age|     city|
+---+-----+----+---------+
|100| John|  35|  Georgia|
|101| Mike|  25| New York|
|103| Mary|  22|    Texas|
|104|Smith|  25|     null|
|105| Jake|null|  Florida|
+---+-----+----+---------+

1 Ответ

2 голосов
/ 05 апреля 2020

Использовать .groupBy и при агрегировании Использовать first/last встроенные искровые функции с игнорированием нуля до true.

//using first function
inputDF.groupBy("id","name").
agg(first("age",true).alias("age"),first("city",true).alias("city")).
orderBy("id").
show()

//using last function
inputDF.groupBy("id","name").
agg(last("age",true).alias("age"),last("city").alias("city")).
orderBy("id").
show()

//+---+-----+----+--------+
//| id| name| age|    city|
//+---+-----+----+--------+
//|100| John|  35| Georgia|
//|101| Mike|  25|New York|
//|103| Mary|  22|   Texas|
//|104|Smith|  25|    null|
//|105| Jake|null| Florida|
//+---+-----+----+--------+
...