Для всех специалистов по данным в какой-то момент времени мы все сталкивались с ситуацией, когда нам нужно обрабатывать крупномасштабные данные в нашем конвейере разработки моделей. Если вы работаете в группах машинного обучения/искусственного интеллекта в крупных организациях, почти неизбежно в какой-то момент вам понадобится использовать Hive. Hive — это SQL-движок для работы с большими данными, построенный на базе Hadoop (инфраструктура больших данных), который упрощает выполнение SQL-запросов к крупномасштабным данным для пользователей Hadoop. Это позволяет пользователям SQL использовать Hadoop для запросов к большим данным без необходимости писать код Hadoop Map-Reduce.

Почему Hive для Data Scientist?

Теперь вы можете возразить, что как специалист по данным я мог выжить без Hive в течение многих лет, почему сейчас? Не каждый анализ/модель нужно строить/масштабировать для больших данных. Хотя это может быть правдой во многих сценариях, но по мере того, как вы будете работать с различными командами по бизнесу/продукту в своей организации, вы скоро поймете, что модель, которую вы построили в прошлом году, нуждается в повторной калибровке на новых данных, поскольку объем данных увеличился. увеличилось в 10 раз по сравнению с тем, что ваша организация видела в прошлом году. Или ваш код разработки функций теперь должен работать с большим объемом данных, чтобы генерировать те же самые старые функции, которые вы разработали для крошечной модели. Код Python с одним узлом не может справиться с таким сценарием, и вам нужно будет увеличить масштаб. Именно здесь вы почувствуете потребность в инструментах для работы с большими данными в своей карьере в области науки о данных.

Кроме того, можно утверждать, что мы отбираем данные и создаем статистически значимую выборку населения и используем эту выборку для задач в конвейере науки о данных. Но и здесь вы обнаружите, что необходимо провести некоторый анализ всего набора данных. Например, вам нужно знать, сколько людей ходили в один и тот же ресторан за последние 6 месяцев. вы не можете полагаться на выборку здесь, так как вы можете исключить группу людей, которые важны для дальнейшего анализа, должен ли этот ресторан быть включен в вашу окончательную модель или нет. Кроме того, если вы являетесь инженером по машинному обучению, вы можете быть вовлечены в этапы разработки/производства модели, такие как разработка функций или агрегация функций и т. д., которые иногда полагаются на инструменты больших данных, такие как кусты, искры и т. д., для выполнения таких задач.

Если вы все еще не убеждены, подумайте об этом как о модном новом перышке, которое должно быть в вашей кепке. Излишне говорить, что это определенно сделает ваше резюме привлекательным для всех компаний, имеющих дело с терабайтами данных. Подождите, разве это не каждая крупная компания в наши дни? Организации получают данные из самых разных источников в сегодняшнюю эпоху Интернета вещей. Эти данные будут со временем просто увеличиваться, что усложнит выполнение задач машинного обучения в коде Python с одним узлом. Это делает интеграцию инструментов больших данных с современным машинным обучением почти неизбежной.

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

  1. Разделение данных

Я не могу не подчеркнуть преимущества этого шага. Я настоятельно рекомендую разделять ваши данные с самого начала . Например, если вы получаете ежедневные данные о потребительской активности, попробуйте объединить все данные за этот день в каталоге, как показано ниже:

So, essentially, you should organize your data as below directories:
/activity/consumer/20220707/activity.txt
/activity/consumer/20220708/activity.txt
/activity/consumer/20220709/activity.txt

Теперь, когда нужно запустить анализ в Hive, добавьте раздел для этого дня в таблицу Hive. Например, вы можете использовать приведенный ниже оператор, чтобы вставить вышеуказанные данные в вашу таблицу кустов (скажем, cons_act) в виде раздела:

> alter table cons_act add partition(date='20220709') location '/activity/consumer/20220709/';

Вы будете выполнять этот шаг каждый день, чтобы загрузить данные за этот день в Hive. Этот шаг со временем избавит вас от проблем с производительностью. Когда у вас есть секционированные данные, теперь вы можете указать диапазоны дат в качестве предложения where в своем запросе, и механизм Hive будет загружать только эти конкретные даты по сравнению со всем диапазоном данных и, следовательно, уменьшает время выполнения вашего коллектора запросов.

Ниже приведены несколько примеров того, как это сделать:

> select * from cons_act where date='20220709'; 
> select * from const_act where date >='20220707' and date <='20220709';
> select * from cons_act where date like '202207%'; 
> select * from cons_act where date like '2022%'; 

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

2. Указание памяти картографа и редуктора

Задания Hive выполняются как набор задач сопоставления и редьюсера. Подробнее об этом здесь. По умолчанию каждая задача получает фиксированную память преобразователя и редуктора. Когда вы запускаете задания Hive над своими большими данными, иногда вы можете видеть, что ваши задания снова и снова уничтожаются на этапе сопоставления/редукции с ошибкой сопоставления/уменьшения памяти, превышающей пределы. Если вы проверите журналы, вы увидите такие ошибки в задачах картографа/редуктора прямо перед тем, как ваша работа будет уничтожена.

В таких сценариях приведенные ниже настройки куста могут помочь вам увеличить память картографа/редьюсера для вашей работы:

> set mapreduce.map.memory.mb=8000;
> set mapreduce.reduce.memory.mb=10000;

Вышеупомянутые настройки относятся к отдельным уровням задач картографа/редьюсера. Здесь я изменил память маппера для каждой задачи маппера на 8 ГБ и для редуктора на 10 ГБ. И он ограничен максимальным объемом памяти контейнера, настроенным администраторами кластера Hadoop. Если вы установите значение памяти выше этого предела, ваше задание не запустится, так как оно запрещено механизмом управления ресурсами Hadoop.

3. Обработка асимметрии данных

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

Когда вы пытаетесь выполнить некоторый анализ этих полей или создать функции вокруг таких полей, ваши задания начнут испытывать «асимметрию», и это приведет к тому, что все запросы, которые работают в целом, начнут давать сбои или будут работать медленнее. Эта медлительность возникает в последних нескольких редукторах в вашей работе (редюсеры сокращают данные, т. е. выполняют этап агрегирования, например, агрегируют активность пользователей в течение дня путем объединения таблицы почасовой активности с таблицей пользователей).

Здесь вы можете использовать приведенную ниже настройку куста, чтобы механизм куста неявно обрабатывал такую ​​асимметрию в соединении:

> set hive.optimize.skewjoin=true;

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

> set hive.skewjoin.key=60000;

Это означает, что если ключ в вашем запросе (например, час дня в приведенном выше примере) имеет строки более 60000, то куст будет рассматривать его как искаженный ключ в этой операции соединения и обрабатывать его особым образом, чтобы уменьшить задержку задания. вызвано обработкой этого ключа с искажением данных.

4. Боковое соединение карты

Наиболее распространенной операцией, которую необходимо выполнить в любой нормализованной базе данных, является соединение таблиц. Hive предоставляет обширный набор оптимизаций для запросов, включающих соединения. Обычно у вас будут данные в нескольких таблицах, которые вам может понадобиться объединить по ключу соединения, чтобы, наконец, выбрать необходимые столбцы из двух разных таблиц. Вот тут-то и появляется «присоединение к карте» Hive. Соединение карты — это операция, которая позволяет нам вывести небольшую таблицу из двух в объединении в памяти в виде карты и, следовательно, в целом ускорить выполнение вашего запроса. Ниже показано, как вы можете указать меньшую из ваших таблиц в качестве соединения карты:

> set hive.auto.convert.join=true;
> select user_details.user_name, user_details.user_age, hourly_act.num_of_games, hourly_act.active_min from user_details join hourly_act on user_details.userid = hourly_act.user_id;

В приведенном выше запросе наша таблица «user_details» будет небольшой и будет содержать такие данные о пользователе, как идентификатор, имя и возраст, но в таблице «почасовая активность» будут записи от всех пользователей в любое время дня. Добавляя настройку автоматического преобразования hive перед запуском этой настройки, мы указываем hive перенести таблицу user_details в память, и это ускорит наш многообразие запросов.

С приведенной выше настройкой связан еще один параметр, который можно использовать для указания небольшого размера таблицы:

> set hive.smalltable.filesize=40000000;

Я нахожу этот параметр очень полезным, когда размер моей маленькой таблицы превышает ограничение по умолчанию, и, следовательно, дает мне возможность использовать в памяти «немного большую» маленькую таблицу. В приведенной выше команде я знаю, что размер моей таблицы user_details составляет 40 МБ. Итак, я установил значение hive.smalltable.filesize равным 40 МБ, что перезаписывает настройку по умолчанию с 25 МБ на 40 МБ.

5. Тайм-аут задачи

Еще один важный параметр при работе с большими данными — тайм-аут на уровне задач картографа/редьюсера. Этот параметр особенно важен при выполнении запросов с предложениями where и group by. Запросы такого типа в сочетании с проблемами асимметрии данных иногда приводят к тому, что некоторые задачи сопоставления/редьюсера выполняются в течение длительного времени. Это также приводит к тому, что выполняющаяся задача пропускает сообщение пульса обратно мастеру приложения (главному узлу, который наблюдает за состоянием задач всего куста), который мастер ожидает каждые 10 минут (значение по умолчанию: 600000). В тех случаях, когда я не вижу проблем с заданием, но задачи выполняются в течение длительного времени, а задание внезапно прекращается, я обнаружил, что это проблема. В приведенной ниже команде я могу обойти эту проблему, установив для этого значения большее значение, например 3600000 миллисекунд, т.е. 30 мин.

> set mapred.task.timeout=3600000;

Это гарантирует, что каждая задача в моем задании куста может выполняться в течение 30 минут, прежде чем она отправит сообщение пульса мастеру приложения. Это гарантирует, что задание не будет уничтожено из-за того, что это сообщение не будет доходить до мастера приложения каждые 10 минут, а будет ждать увеличенного тайм-аута в 30 минут перед завершением задания.

Это подводит нас к концу этого блога о хаках оптимизации Hive. Надеюсь, вы сможете использовать их в своих заданиях в Hive и помочь в отладке определенных проблем, с которыми вы сталкиваетесь в процессе моделирования, не нуждаясь в помощи инженеров по работе с большими данными. А также рассмотрение их с самого начала в ваших запросах иногда избавляет от многих проблем в дальнейшем и помогает легко масштабировать эти запросы.

Если вам нравится этот блог и вы хотите узнать больше по таким интересным темам, как наука о данных и большие данные, присоединяйтесь к medium.com. Это дает вам полный доступ к большему количеству таких историй на medium.com.