Итерация подсчета очков

Это часть 5 мини-серии о разрешении сущностей. Посмотрите часть 1, часть 2, часть 3, часть 4, если вы ее пропустили.

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

На высоком уровне этот процесс выглядит как

  1. Пример из исходных выходных данных функции наивной оценки
  2. Вручную проверьте и пометьте выбранные пары кандидатов
  3. Оцените точность баллов, сравнив ручную метку и распределение баллов
  4. Улучшение критериев принятия решения путем введения дополнительной функции сравнения, где это оправдано и целесообразно.
  5. Загрузите метки и функции в алгоритм классификации, чтобы узнать оптимальную функцию оценки
  6. Повторяйте до тех пор, пока не будет достигнут приемлемый уровень точности.

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

  1. Определенные совпадения и определенные несовпадения не заслуживают рассмотрения. Фактически это означает, что пары, получившие оценку 0 (нет совпадения ни по одной функции) и 1 (полное совпадение по всем функциям), должны быть отфильтрованы.
  2. Стоит продумать лучший визуальный макет, чтобы максимально упростить просмотр и маркировку человеком. Есть такие инструменты, как Snorkel, чтобы помочь с этим типом рабочего процесса. В нашем примере мы выбрали относительно низкий подход к объединению соответствующих функций между парами кандидатов в объединенное строковое значение, чтобы упростить их сравнение.
  3. Могут быть случаи, когда вы захотите использовать стратифицированную выборку. Например, вы можете больше сосредоточиться на парах кандидатов между записями из разных исходных систем и тратить меньше времени на просмотр пар кандидатов из одного источника. Вы также можете по-разному взвесить разные диапазоны оценки сходства. Мы не сделали этого в примере кода, но это несложно реализовать с помощью метода PySpark sampleBy

Глядя на выборку выходных данных, мы сразу видим, что использованная нами упрощенная функция оценки далека от совершенства. Очевидно, что одна из пар кандидатов с наивысшим баллом между adobe creative suite cs3 web standard upsell
и adobe creative suite cs3 web standard [mac] не является совпадением. На самом деле существует довольно много примеров такого несоответствия, когда обновленная версия продукта очень похожа на исходный продукт. Одним из возможных подходов к решению этой проблемы является введение еще одной функции, которая указывает, является ли продукт расширением / обновлением / дополнительными продажами по сравнению с полнофункциональной версией.

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

Стоит отметить несколько практических вещей

  1. Даже с хорошими стратегиями блокировки большая часть пар кандидатов может оказаться явным несовпадением. Перед применением модели их полезно отфильтровать. Это уменьшает дисбаланс классов соответствия и несоответствия, что может негативно повлиять на эффективность модели. В нашем примере мы отфильтровали все пары ниже порога 0,06. Это выбирается несколько произвольно, вручную проверяя выбранные пары кандидатов, и может быть скорректировано по мере необходимости.
  2. По возможности полезно дополнять человеческие ярлыки дополнительными ярлыками, основанными на правилах программы. Чем больше размеченных данных должен изучить алгоритм, тем лучше он будет работать. В нашем примере мы решили пометить пары кандидатов, у которых overall_sim = 1 или где name_tfidf_sim = 1, как программное совпадение. Интуиция здесь заключается в том, что если название точно совпадает, мы можем быть уверены, что эти два списка являются одним и тем же продуктом. С другой стороны, мы решили пометить пары кандидатов, у которых overall_sim меньше 0,12. Это снова выбрано несколько произвольно, основываясь на выборке выходных данных. Эти пороговые значения можно и нужно настраивать как часть итерации.
  3. Мы решили использовать реализацию классификатора случайного леса в Scikit-learn для нашего примера использования, потому что он предлагает более гибкие API для настройки и оценки гиперпараметров. Но для более масштабных сценариев использования, которые не помещаются в память на одном узле, может потребоваться использование библиотек PySpark ML, которые реализуют ряд алгоритмов классификации, которые хорошо интегрируются с остальной частью экосистемы PySpark.

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

Стоит отметить использование pandas_udf, который может обеспечить гораздо лучшую производительность, чем стандартные udf, за счет более эффективной сериализации с помощью Apache Arrow и более эффективных векторизованных вычислений с помощью numpy. Чтобы узнать больше о pandas_udf, я рекомендую прочитать примеры здесь.

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

Ознакомьтесь с заключительной частью по генерации сущностей.