Spark groupByKey альтернатива

В соответствии с лучшими практиками Databricks Spark groupByKey следует избегать, поскольку обработка Spark groupByKey работает таким образом, что информация будет сначала перетасоваться между рабочими, а затем будет выполнена обработка. Объяснение

Итак, мой вопрос в том, каковы альтернативы для groupByKey таким образом, что он будет возвращать следующее распределенным и быстрым способом?

// want this
{"key1": "1", "key1": "2", "key1": "3", "key2": "55", "key2": "66"}
// to become this
{"key1": ["1","2","3"], "key2": ["55","66"]}

Мне кажется, что, возможно, aggregateByKey или glom могли сделать это сначала в разделе (map), а затем объединить все списки вместе (reduce).

Ответ 1

groupByKey отлично подходит для случая, когда нам нужен "маленький" набор значений для ключа, как в вопросе.

TL; DR

Предупреждение "не использовать" на groupByKey применяется для двух общих случаев:

1) Вы хотите агрегировать по значениям:

  • НЕ: rdd.groupByKey().mapValues(_.sum)
  • DO: rdd.reduceByKey(_ + _)

В этом случае groupByKey будет тратить ресурсы на материализацию коллекции, а то, что мы хотим, - это один элемент в качестве ответа.

2) Вы хотите группировать очень большие коллекции по клавишам с низкой мощностью:

  • НЕ: allFacebookUsersRDD.map(user => (user.likesCats, user)).groupByKey()
  • ПРОСТО НЕ

В этом случае groupByKey потенциально может привести к ошибке OOM.

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

Все функции группировки, такие как groupByKey, aggregateByKey и reduceByKey полагаются на базу: combineByKey и, следовательно, нет другая альтернатива будет лучше для usecase в вопросе, все они полагаются на один и тот же общий процесс.