Pyspark Window заказать по - PullRequest
       24

Pyspark Window заказать по

0 голосов
/ 15 октября 2018

У меня есть фрейм данных, который выглядит как

+--------+---+------+----+
|group_id| id|  text|type|
+--------+---+------+----+
|       1|  1|   one|   a|
|       1|  1|   two|   t|
|       1|  2| three|   a|
|       1|  2|  four|   t|
|       1|  5|  five|   a|
|       1|  6|   six|   t|
|       1|  7| seven|   a|
|       1|  9| eight|   t|
|       1|  9|  nine|   a|
|       1| 10|   ten|   t|
|       1| 11|eleven|   a|
+--------+---+------+----+

Если я сделаю операцию Window, разделив ее на group_id и упорядочив ее по id, то упорядочу, убедившись, что уже упорядоченные (отсортированные) строки сохраняют тот же порядок?

например,

window_spec = Window.partitionBy(df.group_id).orderBy(df.id)
df = df.withColumn("row_number", row_number().over(window_spec))

всегда будет

+--------+---+------+----+------+                                               
|group_id| id|  text|type|row_number|
+--------+---+------+----+------+
|       1|  1|   one|   a|     1|
|       1|  1|   two|   t|     2|
|       1|  2| three|   a|     3|
|       1|  2|  four|   t|     4|
|       1|  5|  five|   a|     5|
|       1|  6|   six|   t|     6|
|       1|  7| seven|   a|     7|
|       1|  9| eight|   t|     8|
|       1|  9|  nine|   a|     9|
|       1| 10|   ten|   t|    10|
|       1| 11|eleven|   a|    11|
+--------+---+------+----+------+

В двух словах, мой вопрос заключается в том, как spark Window orderBy обрабатывает уже упорядоченные (отсортированные) строки?Я предполагаю, что он стабилен, то есть он не меняет порядок уже упорядоченных строк, но я не смог найти ничего связанного с этим в документации.Как я могу убедиться, что мое предположение верно?

Спасибо.

1 Ответ

0 голосов
/ 17 октября 2018

Во-первых, чтобы настроить контекст для тех читателей, которые могут не знать определения стабильной сортировки, я процитирую этот ответ StackOverflow Джои Адамса

"Алгоритм сортировки называется стабильным, если два объекта с одинаковыми ключами отображаются в одинаковом порядке в отсортированном выводе, как они отображаются во входном массиве для сортировки "- Джои Адамс

Теперь оконная функцияIn spark можно рассматривать как Spark, обрабатывающий мини-фреймы DataFrames всего вашего набора, где каждый мини-фрейм DataFrame создается по указанному ключу - в данном случае «group_id».

То есть, если у поставляемого фрейма данных "group_id" = 2, мы получим две Windows, где первая содержит только данные с "group_id" = 1, а другая - "group_id" = 2.

Это важно отметить, потому что мы могли бы протестировать влияние вызова .orderBy () на примерный фрейм данных, не беспокоясь о том, что происходит с окном.Чтобы подчеркнуть происходящее:

  1. Данные разделены указанным ключом
  2. Затем преобразования применяются к «мини-фреймам данных», созданным в каждом окне

Следовательно, для предварительно отсортированного ввода, такого как:

df = spark.createDataFrame(
    [
        {'group_id': 1, 'id': 1, 'text': 'one', 'type': 'a'},
        {'group_id': 1, 'id': 1, 'text': 'two', 'type': 't'},
        {'group_id': 1, 'id': 2, 'text': 'three', 'type': 'a'},
        {'group_id': 1, 'id': 2, 'text': 'four', 'type': 't'},
        {'group_id': 1, 'id': 5, 'text': 'five', 'type': 'a'},
        {'group_id': 1, 'id': 6, 'text': 'six', 'type': 't'},
        {'group_id': 1, 'id': 7, 'text': 'seven', 'type': 'a'},
        {'group_id': 1, 'id': 9, 'text': 'eight', 'type': 't'},
        {'group_id': 1, 'id': 9, 'text': 'nine', 'type': 'a'},
        {'group_id': 1, 'id': 10, 'text': 'ten', 'type': 't'},
        {'group_id': 1, 'id': 11, 'text': 'eleven', 'type': 'a'}
    ]
)

+--------+---+------+----+
|group_id| id|  text|type|
+--------+---+------+----+
|       1|  1|   one|   a|
|       1|  1|   two|   t|
|       1|  2| three|   a|
|       1|  2|  four|   t|
|       1|  5|  five|   a|
|       1|  6|   six|   t|
|       1|  7| seven|   a|
|       1|  9| eight|   t|
|       1|  9|  nine|   a|
|       1| 10|   ten|   t|
|       1| 11|eleven|   a|
+--------+---+------+----+

Мы применяем:

df.orderBy('id').show()

В результате:

+--------+---+------+----+
|group_id| id|  text|type|
+--------+---+------+----+
|       1|  1|   one|   a|
|       1|  1|   two|   t|
|       1|  2| three|   a|
|       1|  2|  four|   t|
|       1|  5|  five|   a|
|       1|  6|   six|   t|
|       1|  7| seven|   a|
|       1|  9|  nine|   a|
|       1|  9| eight|   t|
|       1| 10|   ten|   t|
|       1| 11|eleven|   a|
+--------+---+------+----+

Сначала этокажется стабильным, но давайте применим это к DataFrame со строкой с text = "two", замененной строкой с text = "three":

df = spark.createDataFrame(
    [
        {'group_id': 1, 'id': 1, 'text': 'one', 'type': 'a'},
        {'group_id': 1, 'id': 2, 'text': 'three', 'type': 'a'},
        {'group_id': 1, 'id': 1, 'text': 'two', 'type': 't'},
        {'group_id': 1, 'id': 2, 'text': 'four', 'type': 't'},
        {'group_id': 1, 'id': 5, 'text': 'five', 'type': 'a'},
        {'group_id': 1, 'id': 6, 'text': 'six', 'type': 't'},
        {'group_id': 1, 'id': 7, 'text': 'seven', 'type': 'a'},
        {'group_id': 1, 'id': 9, 'text': 'eight', 'type': 't'},
        {'group_id': 1, 'id': 9, 'text': 'nine', 'type': 'a'},
        {'group_id': 1, 'id': 10, 'text': 'ten', 'type': 't'},
        {'group_id': 1, 'id': 11, 'text': 'eleven', 'type': 'a'}
   ]
)

+--------+---+------+----+
|group_id| id|  text|type|
+--------+---+------+----+
|       1|  1|   one|   a|
|       1|  2| three|   a|
|       1|  1|   two|   t|
|       1|  2|  four|   t|
|       1|  5|  five|   a|
|       1|  6|   six|   t|
|       1|  7| seven|   a|
|       1|  9| eight|   t|
|       1|  9|  nine|   a|
|       1| 10|   ten|   t|
|       1| 11|eleven|   a|
+--------+---+------+----+

Затем примените:

df.orderBy(df.id).show()

Что приводит к:

+--------+---+------+----+
|group_id| id|  text|type|
+--------+---+------+----+
|       1|  1|   two|   t|
|       1|  1|   one|   a|
|       1|  2|  four|   t|
|       1|  2| three|   a|
|       1|  5|  five|   a|
|       1|  6|   six|   t|
|       1|  7| seven|   a|
|       1|  9|  nine|   a|
|       1|  9| eight|   t|
|       1| 10|   ten|   t|
|       1| 11|eleven|   a|
+--------+---+------+----+

Как видите, даже если строки text = "one" и text = "two" отображаются в одном и том же порядке, .orderBy () меняет их местами.Таким образом, мы можем предположить, что .orderBy () не является стабильной сортировкой.

...