ТЕХНОЛОГИЯ ЭКСПЕДИА ГРУПП - ПРОГРАММНОЕ ОБЕСПЕЧЕНИЕ

Подробное описание функций массива Apache Spark

Практическое руководство по использованию функций массива

В этом посте мы узнаем о функциях массива Apache Spark на примерах, показывающих, как работает каждая функция. Вам также могут быть интересны мои предыдущие сообщения об Apache Spark.

Примечание: в следующих примерах используется Scala API. Для вашего удобства записная книжка Zeppelin, экспортированная как файл JSON, а также файл Scala доступны на GitHub.

Настраивать

Сначала нам нужно импортировать функции, которые мы рассмотрим в этом блоге.

Давайте создадим несколько фреймов данных Spark, которые мы будем использовать, чтобы узнать о различных функциях массивов.

Здесь мы создали два DataFrames df и full_df, которые содержат два столбца и три столбца соответственно.

Проверить схему

Давайте проверим схему указанного выше DataFrame full_df

Вывод показывает, что col1 - это строковый тип, а array_col1 и array_col2 - массив:

root
|-- col1: string (nullable = true)
|-- array_col1: array (nullable = true)
|    |-- element: integer (containsNull = true)
|-- array_col2: array (nullable = true)
|    |-- element: integer (containsNull = true)

Аналогично для DataFramedf схема выглядит так:

root
|-- col1: string (nullable = true)
|-- array_col2: array (nullable = true)
|    |-- element: integer (containsNull = true)

В следующих примерах мы будем использовать df для функций, которые принимают один массив в качестве входных данных, и df_full для функций, которые принимают два массива в качестве входных данных.

Функции для работы с массивами

array_contains

Если нам нужно найти определенный элемент в массиве, мы можем использовать функцию array_contains. Эта функция возвращает истину, если значение присутствует в массиве, и ложь в противном случае.

Выход:

+----+------------------+------+
|col1|        array_col2|result|
+----+------------------+------+
|   x|   [1, 2, 3, 7, 7]|  true|
|   z|[3, 2, 8, 9, 4, 9]|  true|
|   a|      [4, 5, 2, 8]| false|
+----+------------------+------+

Мы ищем значение «3» в столбце массива array_col2 и получаем true для первых двух строк, где присутствует «3», и false для последнего столбца, поскольку «3» - это нет.

array_distinct

Эта функция возвращает только отдельные значения из массива и удаляет повторяющиеся значения.

Выход:

+----+------------------+---------------+
|col1|        array_col2|         result|
+----+------------------+---------------+
|   x|   [1, 2, 3, 7, 7]|   [1, 2, 3, 7]|
|   z|[3, 2, 8, 9, 4, 9]|[3, 2, 8, 9, 4]|
|   a|      [4, 5, 2, 8]|   [4, 5, 2, 8]|
+----+------------------+---------------+

Повторяющиеся значения были удалены, и в столбце массива result представлены только отдельные значения.

array_except

Эта функция возвращает элементы из первого массива, которых нет во втором массиве. Это логически эквивалентно установке операции вычитание.

Выход:

+----+------------------+------------------+---------+
|col1|        array_col1|        array_col2|   result|
+----+------------------+------------------+---------+
|   x|   [4, 6, 7, 9, 2]|   [1, 2, 3, 7, 7]|[4, 6, 9]|
|   z|[7, 5, 1, 4, 7, 1]|[3, 2, 8, 9, 4, 9]|[7, 5, 1]|
|   a|      [3, 8, 5, 3]|      [4, 5, 2, 8]|      [3]|
+----+------------------+------------------+---------+

Столбец result содержит элементы, которые присутствуют только в array_col1, но отсутствуют в array_col2. Например, в первой строке столбец result содержит [4, 6, 9], потому что эти элементы присутствуют в array_col1, но не в array_col2.

array_intersect

Эта функция возвращает общие элементы из обоих массивов. Это логически эквивалентно установке операции пересечение.

Выход:

+----+------------------+------------------+------+
|col1|        array_col1|        array_col2|result|
+----+------------------+------------------+------+
|   x|   [4, 6, 7, 9, 2]|   [1, 2, 3, 7, 7]|[7, 2]|
|   z|[7, 5, 1, 4, 7, 1]|[3, 2, 8, 9, 4, 9]|   [4]|
|   a|      [3, 8, 5, 3]|      [4, 5, 2, 8]|[8, 5]|
+----+------------------+------------------+------+

Столбец result содержит элементы, общие для обоих столбцов массива (array_col1 и array_col2). Например, в первой строке столбец result содержит [7, 2], потому что эти элементы присутствуют как вarray_col1, так и в array_col2.

array_join

Эта функция объединяет все элементы массива на основе разделителя, определенного вторым аргументом.

Выход:

+----+------------------+-----------+
|col1|        array_col2|     result|
+----+------------------+-----------+
|   x|   [1, 2, 3, 7, 7]|  1,2,3,7,7|
|   z|[3, 2, 8, 9, 4, 9]|3,2,8,9,4,9|
|   a|      [4, 5, 2, 8]|    4,5,2,8|
+----+------------------+-----------+

Столбец result содержит строку, которая представляет собой объединение всех элементов массива с использованием указанного разделителя (в этом примере запятая).

Примечание: если есть какие-либо значения NULL, мы можем заменить третий аргумент (nullReplacement) любым строковым значением.

array_max

Эта функция возвращает максимальное значение из массива.

Выход:

+----+------------------+------+
|col1|        array_col2|result|
+----+------------------+------+
|   x|   [1, 2, 3, 7, 7]|     7|
|   z|[3, 2, 8, 9, 4, 9]|     9|
|   a|      [4, 5, 2, 8]|     8|
+----+------------------+------+

Столбец result содержит максимальное значение из каждого массива в строке. Например, в первой строке столбец result содержит «7», потому что это максимальный элемент в массиве [1, 2, 3, 7, 7].

array_min

Эта функция возвращает минимальное значение из массива.

Выход:

+----+------------------+------+
|col1|        array_col2|result|
+----+------------------+------+
|   x|   [1, 2, 3, 7, 7]|     1|
|   z|[3, 2, 8, 9, 4, 9]|     2|
|   a|      [4, 5, 2, 8]|     2|
+----+------------------+------+

Столбец result содержит минимальное значение из каждого массива в строке. Например, в первой строке столбец result содержит «1», потому что это минимальный элемент в массиве [1, 2, 3, 7, 7].

array_position

Эта функция возвращает позицию первого появления указанного элемента. Если элемент отсутствует, возвращается 0.

Давайте попробуем найти положение элемента, скажем, «7» из столбца array_col2.

Выход:

+----+------------------+------+
|col1|        array_col2|result|
+----+------------------+------+
|   x|   [1, 2, 3, 7, 7]|     4|
|   z|[3, 2, 8, 9, 4, 9]|     0|
|   a|      [4, 5, 2, 8]|     0|
+----+------------------+------+

В первой строке мы получаем позицию «4», потому что «7» впервые встречается в позиции четыре. Для остальных строк мы получаем «0», потому что «7» отсутствует.

array_remove

Эта функция удаляет все вхождения элемента из массива.

Удалим элемент «7» из столбца array_col2.

Выход:

+----+------------------+------------------+
|col1|        array_col2|            result|
+----+------------------+------------------+
|   x|   [1, 2, 3, 7, 7]|         [1, 2, 3]|
|   z|[3, 2, 8, 9, 4, 9]|[3, 2, 8, 9, 4, 9]|
|   a|      [4, 5, 2, 8]|      [4, 5, 2, 8]|
+----+------------------+------------------+

Все вхождения элемента «7» удаляются из массива.

array_repeat

Эта функция создает массив, который повторяется, как указано вторым аргументом.

Выход:

+----+------------------+----------------------------------------+ |col1|array_col2        |result                                  | +----+------------------+----------------------------------------+ |x   |[1, 2, 3, 7, 7]   |[[1, 2, 3, 7, 7], [1, 2, 3, 7, 7]]      | |z   |[3, 2, 8, 9, 4, 9]|[[3, 2, 8, 9, 4, 9], [3, 2, 8, 9, 4, 9]]| |a   |[4, 5, 2, 8]      |[[4, 5, 2, 8], [4, 5, 2, 8]]            | +----+------------------+----------------------------------------+

Массив из array_col2 повторился 2 раза в столбце result. Например, в первой строке столбец result содержит массив [1, 2, 3, 7, 7] twice.

array_sort

Эта функция сортирует элементы массива в порядке возрастания.

Выход:

+----+------------------+------------------+
|col1|        array_col2|            result|
+----+------------------+------------------+
|   x|   [1, 2, 3, 7, 7]|   [1, 2, 3, 7, 7]|
|   z|[3, 2, 8, 9, 4, 9]|[2, 3, 4, 8, 9, 9]|
|   a|      [4, 5, 2, 8]|      [2, 4, 5, 8]|
+----+------------------+------------------+

Массив в столбце result отсортирован по возрастанию. Например, в последней строке результат столбца содержит [2, 4, 5, 8], который отсортирован в порядке возрастания.

array_union

Эта функция возвращает объединение всех элементов из входных массивов.

Выход:

+------------------+------------------+------------------------+ |array_col1        |array_col2        |result                  | 
+------------------+------------------+------------------------+ 
|[4, 6, 7, 9, 2]   |[1, 2, 3, 7, 7]   |[4, 6, 7, 9, 2, 1, 3]   | 
|[7, 5, 1, 4, 7, 1]|[3, 2, 8, 9, 4, 9]|[7, 5, 1, 4, 3, 2, 8, 9]| 
|[3, 8, 5, 3]      |[4, 5, 2, 8]      |[3, 8, 5, 4, 2]         | 
+------------------+------------------+------------------------+

Примечание: опущено col1, чтобы соответствовать результату здесь, в блоке кода.

Столбец result содержит объединение массивов из столбца array_col1 и array_col2 и содержит только различные значения.

array_overlap

Эта функция проверяет, является ли хотя бы один элемент общим / перекрывающимся в массивах. Он возвращает true, если хотя бы один элемент является общим в обоих массивах, и false в противном случае. Он возвращает значение NULL, если хотя бы один из массивов имеет значение NULL.

Выход:

+----+------------------+------------------+------+
|col1|array_col1        |array_col2        |result|
+----+------------------+------------------+------+
|x   |[4, 6, 7, 9, 2]   |[1, 2, 3, 7, 7]   |true  |
|z   |[7, 5, 1, 4, 7, 1]|[3, 2, 8, 9, 4, 9]|true  |
|a   |[3, 8, 5, 3]      |[4, 5, 2, 8]      |true  |
+----+------------------+------------------+------+

Все значения в столбце result равны true, потому что у нас есть хотя бы один общий элемент в array_col1 и array_col2 для всех строк. Например, в первой строке result столбец - это true, потому что элементы «2» и «7» присутствуют в обоих столбцах array_col1 и array_col2.

array_zip

Эта функция объединяет i-й элемент массива и возвращает массив ‹struct›.

Поскольку оба столбца массива имеют одинаковое количество значений, давайте удалим некоторые значения из одного столбца массива и посмотрим, как он ведет себя с разными значениями в массиве с помощью операции zip.

Сначала мы удалим элемент «2» из столбца array_col2 массива, а затем попытаемся заархивировать столбец array_col1 с вновь созданным столбцом new_array_col

Выход:

+------------------+---------------+-------------------------------+
|array_col1        |new_array_col  |result                         |
+------------------+---------------+-------------------------------+
|[4, 6, 7, 9, 2]   |[1, 3, 7, 7]   |[[4, 1], [6, 3] ..., [2,]]     |
|[7, 5, 1, 4, 7, 1]|[3, 8, 9, 4, 9]|[[7, 3], [5, 8] ..., [1,]]     |
|[3, 8, 5, 3]      |[4, 5, 8]      |[[3, 4], ... [3,]]             |
+------------------+---------------+-------------------------------+

В первой строке первым элементом столбца result является [4, 1], который представляет собой zip первого элемента из массива array_col1 (4) и new_array_col (1). Кроме того, последний элемент столбца result - [2,] (который представляет собой zip 5-го элемента), а второе значение пусто, потому что в первой строке столбца new_array_col нет 5-го элемента.

Давайте также проверим тип result столбцов.

Выход:

root
|-- result: array (nullable = true)
|    |-- element: struct (containsNull = false)
|    |    |-- array_col1: integer (nullable = true)
|    |    |-- new_array_col: integer (nullable = true)

Тип столбца результата - массив ‹struct›.

concat

Эта функция объединяет все элементы обоих массивов в один.

Выход:

+------------------+------------------+----------------------------+
|array_col1        |array_col2        |result                      |
+------------------+------------------+----------------------------+
|[4, 6, 7, 9, 2]   |[1, 2, 3, 7, 7]   |[4, 6, 7, 9, ..., 3, 7, 7]  |
|[7, 5, 1, 4, 7, 1]|[3, 2, 8, 9, 4, 9]|[7, 5, 1, 4, ..., 9, 4, 9]  |
|[3, 8, 5, 3]      |[4, 5, 2, 8]      |[3, 8, 5, 3, 4, 5, 2, 8]    |
+------------------+------------------+----------------------------+

Столбец result содержит массив, который представляет собой объединение массивов в столбцах array_col1 и array_col2.

Примечание. Чтобы уместить результат, мы удалили несколько элементов из столбца result с дисплея.

element_at

Эта функция возвращает элемент по указанному индексу.

Попробуем получить первый элемент из каждого массива.

Выход:

+----+------------------+------+
|col1|array_col2        |result|
+----+------------------+------+
|x   |[1, 2, 3, 7, 7]   |1     |
|z   |[3, 2, 8, 9, 4, 9]|3     |
|a   |[4, 5, 2, 8]      |4     |
+----+------------------+------+

Столбец result содержит первый элемент из каждого массива. Например, в первой строке result содержит «1», потому что это первый элемент в массиве [1, 2, 3, 7, 7].

сплющивать

Эта функция возвращает единственный массив из массива массивов. Если массив имеет глубину более двух уровней, он удаляет один уровень вложенности из массива.

Давайте сначала сгенерируем вложенный массив, используя функцию array_repeat, как описано выше, а затем сгладим вложенный массив.

Выход:

+-----------------------------------+------------------------------+ 
|repeat                             |result                        | 
+-----------------------------------+------------------------------+ 
|[[1, 2, 3, 7, 7], [1, 2, 3, 7, 7]] |[1, 2, 3, 7, 7, 1, 2, 3, 7, 7]| 
|[[3, 2, 8, 9, 4], [3, 2, 8, 9, 4]] |[3, 2, 8, 9, 4, 3, 2, 8, 9, 4]| 
|[[4, 5, 2, 8], [4, 5, 2, 8]]       |[4, 5, 2, 8, 4, 5, 2, 8]      | 
+----------------------------------------+-------------------------+

Столбец result содержит все значения из массива массивов из столбца repeat, но в одном массиве.

map_from_arrays

Эта функция создает столбец карты. Элементы первого столбца будут использоваться для ключей, а второй столбец - для значений.

Выход:

+------------------+------------------+--------------------+ 
|        array_col1|        array_col2|              result| 
+------------------+------------------+--------------------+ 
|   [4, 6, 7, 9, 2]|   [1, 2, 3, 7, 7]|[4 -> 1, 6 -> 2, ...| 
|[7, 5, 1, 4, 7, 1]|[3, 2, 8, 9, 4, 9]|[7 -> 3, 5 -> 2, ...| 
|      [3, 8, 5, 3]|      [4, 5, 2, 8]|[3 -> 4, 8 -> 5, ...| 
+------------------+------------------+--------------------+

Столбец result содержит карту, созданную из обоих входных массивов. Первый элемент в первой строке - это 4 -> 1, где «4» - это ключ, который является первым элементом из первого столбца array_col1, а «1» - это значение ключа, которое является первым элементом из второго столбца array_col2.

задний ход

Эта функция меняет порядок элементов во входном массиве.

Выход:

+----+------------------+------------------+ 
|col1|        array_col2|            result| 
+----+------------------+------------------+ 
|   x|   [1, 2, 3, 7, 7]|   [7, 7, 3, 2, 1]| 
|   z|[3, 2, 8, 9, 4, 9]|[9, 4, 9, 8, 2, 3]| 
|   a|      [4, 5, 2, 8]|      [8, 2, 5, 4]| 
+----+------------------+------------------+

Столбец result содержит обратную сторону массива, присутствующего в столбце array_col2. Например, в первой строке result содержит [7, 7, 3, 2, 1], который является обратным массиву [1, 2, 3, 7, 7] из столбца aray_col2.

тасовать

Эта функция перемешивает элементы массива случайным образом.

Выход:

+----+------------------+------------------+ 
|col1|        array_col2|            result| 
+----+------------------+------------------+ 
|   x|   [1, 2, 3, 7, 7]|   [2, 7, 1, 7, 3]| 
|   z|[3, 2, 8, 9, 4, 9]|[3, 8, 9, 4, 9, 2]| 
|   a|      [4, 5, 2, 8]|      [8, 4, 2, 5]| 
+----+------------------+------------------+

Столбец result содержит перемешанные элементы из столбца array_col2. Другими словами, порядок элементов в столбце result случайный. Например, в первой строке столбец result содержит [2, 7, 1, 7, 3], который представляет собой перемешанный вывод массива [1, 2, 3, 7, 7] из столбца array_col2.

Примечание. Попробуйте выполнить функцию перемешивания несколько раз. Порядок значений в столбце result будет отличаться для каждого выполнения.

размер

Эта функция возвращает количество элементов в массиве или карте.

Выход:

+----+------------------+------+ 
|col1|        array_col2|result| 
+----+------------------+------+ 
|   x|   [1, 2, 3, 7, 7]|     5| 
|   z|[3, 2, 8, 9, 4, 9]|     6| 
|   a|      [4, 5, 2, 8]|     4| 
+----+------------------+------+

Столбец result содержит размер (количество элементов) массива в столбце array_col2. Например, в первой строке столбец result содержит «5», потому что количество элементов в [1, 2, 3, 7, 7] равно 5.

кусочек

Эта функция разбивает массив на подмассив. Мы можем указать начало индекса в качестве второго аргумента и количество элементов в качестве третьего аргумента.

Примечание. Массивы в Spark начинаются с индекса 1. Он также поддерживает отрицательную индексацию для доступа к элементам с последнего.

Давайте попробуем создать подмассив из 3 элементов, начиная с индекса 2.

Выход:

+----+------------------+---------+ 
|col1|        array_col2|   result| 
+----+------------------+---------+ 
|   x|   [1, 2, 3, 7, 7]|[2, 3, 7]| 
|   z|[3, 2, 8, 9, 4, 9]|[2, 8, 9]| 
|   a|      [4, 5, 2, 8]|[5, 2, 8]| 
+----+------------------+---------+

В первой строке result содержит подмассив [2, 3, 7], который создается с 3 элементами из индекса 2 в [1, 2, 3, 7, 7].

sort_array

Эта функция по умолчанию сортирует массив в порядке возрастания. Однако мы можем отсортировать по убыванию со вторым аргументом как asc=false.

Выход:

+----+------------------+------------------+ 
|col1|        array_col2|            result| 
+----+------------------+------------------+ 
|   x|   [1, 2, 3, 7, 7]|   [7, 7, 3, 2, 1]| 
|   z|[3, 2, 8, 9, 4, 9]|[9, 9, 8, 4, 3, 2]| 
|   a|      [4, 5, 2, 8]|      [8, 5, 4, 2]| 
+----+------------------+------------------+

Столбец result отсортирован по убыванию. Например, в первой строке столбец result содержит [7, 7, 3, 2, 1], который является отсортированным по убыванию результатом array[1, 2, 3, 7, 7] из столбца array_col2.

взорваться

Эта функция создает новую строку для каждого элемента массива или карты.

Давайте сначала создадим новый столбец с меньшим количеством значений, которые нужно разнести.

Выход:

+----+---------+ 
|col1|slice_col| 
+----+---------+ 
|   x|   [1, 2]| 
|   z|   [3, 2]| 
|   a|   [4, 5]| 
+----+---------+

slice_col содержит 2 элемента в массиве. Таким образом, после разнесения создается 2 строки для каждого массива.

Теперь попробуем взорвать столб slice_col.

Выход:

+----+---------+------+ 
|col1|slice_col|result| 
+----+---------+------+ 
|   x|   [1, 2]|     1| 
|   x|   [1, 2]|     2| 
|   z|   [3, 2]|     3| 
|   z|   [3, 2]|     2| 
|   a|   [4, 5]|     4| 
|   a|   [4, 5]|     5| 
+----+---------+------+

После разнесения создаются 2 строки для каждого элемента массива в столбце slice_col.

Posexplode

Эта функция создает новую строку для каждого элемента с позицией массива или карты.

Давайте сначала создадим новый столбец с меньшим количеством значений, которые нужно разнести.

А теперь попробуем взорвать slice_col с позиции.

Выход:

+----+---------+---+---+ 
|col1|slice_col|pos|col| 
+----+---------+---+---+ 
|x   |[1, 2]   |0  |1  | 
|x   |[1, 2]   |1  |2  | 
|z   |[3, 2]   |0  |3  | 
|z   |[3, 2]   |1  |2  | 
|a   |[4, 5]   |0  |4  | 
|a   |[4, 5]   |1  |5  | 
+----+---------+---+---+

Здесь были сгенерированы еще 2 столбца как pos (представляют позицию) и col (представляют значение элемента).

Надеюсь, вам понравилось узнавать о работе с различными функциями массивов в Apache Spark. Для удобства на GitHub доступен блокнот, содержащий приведенные выше примеры.

Ссылка