Метрика, которая ломается на масштабе флота
Один агент, сообщающий ложноположительное срабатывание, стоит ревьюеру нескольких минут. Десять тысяч агентов, каждый из которых сообщает ложноположительное срабатывание, стоят ревьюеру рабочей недели, и очередь продолжает расти, пока идёт ревью. Арифметика не тонкая, но её регулярно пропускают: точность сообщается как свойство модели, тогда как стоимость ложноположительного срабатывания — свойство конвейера, который его потребляет.
В этом структурное сходство двух в остальном несвязанных программ. Работа OpenAI по безопасности — поиск и устранение уязвимостей — и её программа агентов для биологических данных обе ставят флот агентов перед корпусом и просят людей вынести решение о том, что возвращается. Узкое место в обоих случаях — не полнота модели на отложенной выборке. Это скорость, с которой небольшое число квалифицированных ревьюеров может подтвердить или отклонить кандидатов. Отчёт об уязвимости требует человека, способного её воспроизвести; биологическая зацепка требует человека, способного судить, стоит ли она запуска в лаборатории. Ни одна из очередей не масштабируется с GPU-часами.
Поэтому полезный вопрос меняется. Вместо того чтобы спрашивать, насколько точен агент, спросите, сколько подтверждённых находок флот производит на единицу внимания ревьюера при заданном бюджете ложноположительных срабатываний. Это другая величина, измеряемая по другой оси, и большинство бенчмарков агентов её не сообщают. Они сообщают доли прохождений на курированных задачах, где каждый выход уже известен как проверяемый, что устраняет ровно ту стоимость триажа, которая доминирует в реальных развёртываниях флотов.
Сдвиг меняет и то, что такое «находка». На масштабе флота находки не являются независимыми вытягиваниями. Они кластеризуются.
Дедупликация — это и есть продукт
Запустите тысячу агентов по одной и той же кодовой базе или одному и тому же корпусу белок-белковых взаимодействий, и они сойдутся. Многие выявят одну и ту же отсутствующую проверку границ, один и тот же подозрительный мотив связывания, одну и ту же некорректную ветвь парсера. Сырой выход выглядит как крупное тело открытий; различных выходов в нём часто малая доля.

Это делает кластеризацию и дедупликацию несущим компонентом, а не приятной постобработкой. Конвейер должен решать, когда два кандидата в находки — это одна находка, и решать это достаточно согласованно, чтобы ревьюер мог доверять группировке. Важны два режима отказа. Избыточное слияние — и действительно различные находки исчезают в одном кластере, что является тихой потерей полноты. Избыточное разделение — и ревьюер видит одну и ту же проблему одиннадцать раз под одиннадцатью описаниями, что есть проблема очереди триажа в маскировке.
Трассировка в стиле согласованности — практика записи того, где набор агентов разошёлся на идентичном или почти идентичном входе, — становится здесь полезной так, что легко упустить. В отладке одного агента это курьёз. Во флоте это сигнал триажа: кластер, в котором многие агенты независимо сходятся, — сильный кандидат, а кластер, в котором агенты расходятся по согласованной границе, говорит ревьюеру, где на самом деле находится решение о суждении. Трасса не является доказательством правильности находки, но это дешёвый априорный сигнал о том, где внимание ревьюера будет потрачено лучше всего.
Честный компромисс в том, что дедупликация сама по себе — решение, имеющее форму модели, со своей собственной частотой ошибок, и её обычно оценивают гораздо менее строго, чем агентов, которым она служит. Слой дедупликации, настроенный на сокращение длины очереди, будет сливать агрессивно и скрывать находки; настроенный на полноту — вернёт очередь, неотличимую от полного отсутствия дедупликации. Поэтому конвейер должен раскрывать решение о кластеризации ревьюеру, а не разрешать его невидимо, и его следует оценивать по тому, ставит ли ранжированный список подтверждённые находки близко к началу, а не по тому, выглядят ли кластеры аккуратно.
Что должен сообщать бенчмарк флота
Бенчмарк, который мы хотели бы для флота обнаружения, — не строка в таблице лидеров. Это кривая, и к ней нужно приложить три вещи.
Выход против часов ревьюера. Отложите подтверждённые находки по вертикальной оси, а часы ревьюера — по горизонтальной, и укажите частоту ложноположительных срабатываний в каждой рабочей точке, а не одно усреднённое число. Кривая важна потому, что предельная находка становится дороже по мере обработки очереди: первый час ревью ловит очевидные кластеры, десятый час перемалывает неоднозначный хвост. Одно число точности полностью скрывает эту форму.

Стоимость на подтверждённую находку, включая триаж. Стоимость вычислений на запуск агента легко измерить, и сама по себе она вводит в заблуждение. Число, определяющее, стоит ли запускать флот, включает проход дедупликации, проход ранжирования и время ревьюера, потому что конфигурация, которая вдвое сокращает вычисления и вдвое увеличивает нагрузку на ревьюера, является регрессией. Сообщайте всю цепочку или не сообщайте ничего.
Воспроизводимость на одном и том же корпусе. Повторно запустите ту же конфигурацию флота на том же корпусе и сообщите, какая доля подтверждённого набора повторяется. Флоты стохастичны так, что это накапливается: сэмплирование, порядок вызовов инструментов и пороги кластеризации взаимодействуют. Конфигурация, чьи подтверждённые находки не повторяются, — не инструмент обнаружения, а генератор случайных чисел с хорошим интерфейсом.
Конкретный механизм, чтобы это измерялось: инструментируйте конвейер так, чтобы каждый кандидат нёс запись о происхождении — от агента, который его произвёл, через кластер, в который он попал, до решения ревьюера, которое его разрешило. Эта запись позволяет команде вычислить кривую выхода постфактум, а не восстанавливать её по памяти, и именно она делает повторный запуск сопоставимым с исходным.
Ничто из этого не бесплатно. Инструментирование добавляет задержку и хранение, ранжированный список требует модели ранжирования, которая сама нуждается в оценке, а ось часов ревьюера требует организации, достаточно честной, чтобы логировать собственное время ревью. Альтернатива — флот, чей объём выхода растёт быстрее, чем подтверждённые находки, и это тот режим отказа, который бенчмарки сейчас не способны увидеть.
Сначала бюджет внимания ревьюера
Правило проектирования, которое из этого следует, неудобно для команд, мыслящих вычислениями: сначала задайте бюджет ревьюера, затем подгоняйте под него размер флота. Если пропускная способность триажа — фиксированное число часов в неделю, это число определяет, сколько кандидатов конвейер может позволить себе выдать, а размер флота следует из ожидаемого выхода на кандидата. Масштабирование агентов сверх пропускной способности триажа не производит больше открытий. Оно производит более длинную очередь, деморализованную команду ревью и растущий бэклог неразрешённых кандидатов, которые никто не может отличить от шума.
Это переворачивает обычный разговор о масштабировании. Больше агентов полезно, только если слои дедупликации и ранжирования превращают их выход в более короткий и лучше упорядоченный список. Там, где это превращение слабое, дополнительные агенты добавляют стоимость и глубину очереди без подтверждённых находок в оправдание. Организации, которые делают это правильно, обычно относятся к конвейеру триажа как к продукту, а к флоту — как к поставщику для него, и оценивают поставщика по выходу на час ревьюера, а не по тому, сколько кандидатов он может сгенерировать.
Для таких программ, как поиск уязвимостей и генерация биологических зацепок, где этап вынесения решения дорог, а запас квалифицированных ревьюеров фиксирован, эта формулировка — не уточнение. Это разница между флотом, который находит вещи, и флотом, который производит работу.
