Инженерия контекста для исследовательского агента Quant: уровни доказательств и хранилища данных
Инжиниринг контекста для исследовательского агента WorldQuant: правила, наблюдения и убеждения на разных уровнях доказательств, распределённые по журналу операций, хранилищу событий и графу.
Источники: My AI Agent is in ~Top-0.01% of WorldQuant Challenge #4: Context Engineering
Определение того, чему может доверять агент
Представьте исследовательскую среду, управляемую ИИ и созданную для конкурса по квантовым алгоритмам WorldQuant BRAIN. До появления специализированных агентов, проверок жизненного цикла или автономных циклов существует более фундаментальная проблема проектирования: какие утверждения система может считать истинными? Исходные данные поступают в четырех формах, которые почти не имеют общего между собой.
Первым элементом являются официальная документация платформы и турнира, в которой подробно описывается принцип работы языка выражений, какие операторы и наборы данных доступны, а также какие настройки симуляции допускаются. Вторым элементом является методология: три книги Маркоса Лопеса де Прадо предоставляют инструменты для анализа статистики бэктестов, рисков стратегий, проблемы множественных тестов, структуры портфелей и методов проверки гипотез, в то время как книга Игоря Тульчинского «Finding Alphas» практически описывает процесс формирования идей, уровень оборота активов, корреляцию, проблему переобучения, смещение результатов и их стабильность. Третьим элементом является совокупность статей и записей глубоких исследований, посвящённых экономическим аномалиям, участникам рынка и потокам информации; их можно представить в виде графа, связывающего аксиомы, теории, аномалии, механизмы и способы их реализации. Четвертым элементом являются все те данные, которые генерирует проект в процессе работы: результаты симуляций, ежедневные графики прибылей и убытков, корреляции портфелей, статистика устойчивости, проверки платформы, история экспериментов, операционные события, неудачные попытки сборки и извлеченные из них уроки.
Каждый из этих элементов представляет собой контекст, однако они обладают разным уровнем достоверности, и ни один из них не может быть полностью включен в один запрос, один формат документа или одну базу данных. Поэтому проектирование контекста в таких условиях начинается не с ограничений по количеству токенов, а с определения уровней доказательств и создания систем хранения данных, обеспечивающих сохранность каждого уровня.
Слева представлен наивный первоначальный дизайн, в котором правила, книги, статьи и собственные результаты системы сведены в один запрос, причем всем им придается одинаковый вес. Справа каждое утверждение сохраняет свой уровень: правила образуют «стены», убеждения предлагают тесты, наблюдения корректируют убеждения, и ничто внутри этих «стен» не может их изменить.
Три уровня доказательств
Под «доказательством» подразумевается нечто практическое. Для любого утверждения необходимо определить, каких доказательств достаточно, кто несет за них ответственность и что допускается для их опровержения. Эти вопросы решаются с помощью трех уровней.
L1 фиксирует то, что платформа объявляет игрой, используя официальные материалы платформы и турниров. Когда агенту необходимо узнать, какие настройки существуют, что делает оператор, какие проверки должен пройти кандидат или как турнир рассчитывает свои баллы, именно здесь он ищет информацию. Локальная копия может устаревать, но никакой неожиданный эксперимент не может изменить правила.
L2 фиксирует то, что система действительно видела. Сюда входят результаты симуляций, ежедневные показатели PnL, сегодняшний портфель, проверки платформы, операционные события и самое актуальное состояние топ-листа. Каждое измерение сопровождается указанием времени его зафиксирования. Перезапуск ничего не стирает — он создаёт новое наблюдение, поэтому история никогда не упорядочивается задним числом.
L3 содержит то, что система в настоящее время считает полезным. В этом слое находятся книги, статьи, экономические теории, спецификации, данные из знаниевых графов, записанные уроки и элементы, предназначенные для опровержения гипотез. Они определяют следующие действия и могут быть изменены.
Порядок этих уровней не строгий: L1 всегда имеет приоритет перед L2, а L2 — перед L3. Каждый уровень отвечает на другой тип вопросов. При фактическом разногласии между источниками преобладает наиболее убедительный прямой аргумент; поэтому официальное правило имеет приоритет над перефразированием в промпте агента, а взвешенный ответ — над тем, чего можно было ожидать на основе книги. Однако при определении следующих действий правила и показатели уже не могут дать ответа. Именно тогда нужен L3, чтобы сделать обоснованный выбор.
В этой диаграмме отслеживаются три идеи. Эффект отклонения после опубликования финансовых результатов не был устранён методом его опровержения; вместо этого была выявлена причина сбоя, в связи с чем идея была переработана на основе корректировок аналитиков, и было представлено два варианта. Идея, основанная на сравнении с аналогичными активами, изначально представляла собой чистое предположение без никаких доказательств, но всё равно прошла проверку. Идея, связанная с «часами дивидендов», не сработала ни в одной из десяти реализаций, и в результате предположения были сужены до указания только дат выплаты дивидендов. Зелёные квадраты — это варианты, прошедшие проверку платформы; красные — не прошедшие; серые — без каких-либо записей о проверках; а овальные обозначают варианты, которые были представлены для рассмотрения.
Одна база данных может содержать как само измерение (L2), так и его оценку конкретным человеком (L3), что означает, что уровень привязан к самому утверждению, а не к месту его хранения. Соответственно, полезная запись контекста богаче обычного текста. Она должна включать само утверждение, его эпистемический уровень, источник, владельца, область применения, время наблюдения или проверки, степень неопределенности, стабильный идентификатор, а также любые доказательства, способные его скорректировать. Для фактов, которые меняются со временем, полезны две временные шкалы: когда что-то считалось истинным и когда система узнала об этом. API, которые отвечают с задержкой и заполняют исторические данные задним числом, делают эту пробел во времени значимой.
Контекст на самом деле представляет собой небольшую платформу для хранения данных
Каждый магазин отображается в соответствии с его поведением. Журнал хранения собирает доказательства слоями, и через них проходит одна цепочка преемственности; старые события утрачивают значимость. Граф представляет собой пару таблиц, которые в памяти превращаются в многограф, а файлы группируются по этапам их жизненного цикла. Стабильные идентификаторы связывают все эти элементы воедино. Ежедневная прибыль и убыток по-прежнему находится в том месте, где, согласно собственным спецификациям проекта, она должна находиться.
Как только существуют уровни доказательств, становится очевидным ещё один момент: контекст — это не единый корпус данных. Он ведёт себя как небольшая платформа для обработки данных. Самой большой его частью является учётная книга исследований, которая на проверенной рабочей станции представляет собой транзакционную базу данных SQLite. Называть её таблицей экспериментов — значит недооценивать её функции, поскольку она служит учётной книгой доказательств, хранящей несколько групп записей. Одна группа относится к целям исследования, то есть к механизмам, гипотезам, прогнозам и истории реализаций. Другая группа предназначена для хранения данных измерений: ответов платформы, статистики внутри выборки, результатов проверок, ежедневных показателей PnL и метрик стресс-тестов. Третья группа предназначена для интерпретации данных: здесь хранятся атрибуции, выводы и специфические факторы, опровергающие гипотезы. Четвёртая группа связана с управлением: в ней отслеживаются потенциальные решения, одобрения и все события, происходящие на этапе подачи данных. Последним видом является анализ, основанный на материализованных данных: дельты портфеля, экраны корреляции, кэши шаблонов и краткие отчеты о стресс-тестах, все из которых могут быть воссозданы на основе канонических данных.
При аудите было обнаружено несоответствие. В документе с описанием проекта указано, что ежедневные показатели PnL были сохранены в файлах формата Parquet, однако база данных по-прежнему хранит каждую строку. Документ представляет собой утверждение (уровень L3), а база данных — наблюдение (уровень L2), и в случае конфликта преобладает наблюдение.
Далее идет хранилище операционных событий, которое сохраняется в отдельной базе данных SQLite. События в нем могут содержать идентификаторы циклов, пакетов, кандидатов, гипотез, агентов и процессов, а также данные в формате JSON с версионированием. Может возникнуть соблазн объединить их с основным реестром, но требования к хранению различаются. Научные данные являются каноническими и должны сохраняться навсегда. Выходные данные от отладки, события отправки, очереди переходов и временные меры быстро увеличиваются в объеме и могут быть сжаты или удалены по истечении срока. При разделении этих элементов всплеск данных для наблюдения не может привести к увеличению объема или заблокировке научного записи.
Существует также граф знаний — транзакционный граф свойств с преднамеренно простой физической структурой: таблица узлов, таблица рёбер и атрибуты в формате JSON, содержащие данные, специфичные для каждого типа; всё это загружается во внутренний граф для последующего обхода. Транзакционный слой позволяет избежать проблем с повреждением данных и конкурентными ситуациями, характерными для одного огромного файла в формате YAML, в то время как работа в памяти обеспечивает удобство при выполнении логических операций.
Файловая система также считается системой хранения данных. Хранилище содержит недоступные для изменения документы платформы, книги, статьи и генерируемые отчеты, и загрузка всего этого в память была бы ошибкой, поскольку у них разные циклы жизни. Документы платформы никогда не меняются. Технические спецификации находятся под контролем версий в качестве основы для проектирования. Отчеты представляют собой результаты обработки, для которых необходимы зарегистрированные входные данные и способ их повторной генерации. Файлы в памяти — это краткие, читаемые указатели на универсально используемые материалы. Файлы очередей, кэши и журналы — это временные данные операционного состояния, в то время как бинарные файлы моделей, экспорты PnL и крупные снимки состояния лучше хранить в системах объектного хранения, а не в Git.
Истории неудач говорят сами за себя. Один из наиболее эффективных алгоритмов альфа чуть не был отклонён, поскольку учётная книга указывала, что все проверки пройдены, в то время как скрипт анализировал файл с результатами, показывавший значение Шарпа равным 0. У одного из ранних победителей вообще не было записей о принятых решениях, пока шесть недель спустя процедура сверки не предоставила такую информацию. Решение о ставках против алгоритма бета существовало только внутри файла с данными в формате Markdown, поэтому сама учётная книга ничего не сделала бы для предотвращения повторной попытки.
В итоге получается система с множеством типов контекста, хотя почти вся она всё ещё работает на одном ноутбуке. SQLite обрабатывает транзакции, графы отражают взаимосвязи, формат Parquet предназначен для хранения крупных временных рядов, Markdown используется для хранения информации, которую могут просматривать люди, а временные файлы координируют локальные процессы.
Здесь показан один реальный механизм без указания его названия. Слева представлена его преемственность в графе знаний, а справа — каждая гипотеза, эксперимент и кандидат, которые подвергли его тестированию. Некоторые сбои возникали при каждой реализации, тогда как другие были характерны только для одной из них. Обе части не имеют ничего общего, кроме идентификатора, расположенного вдоль разделительной линии, и этот единственный ключ достаточен для объединения их в компактный пакет контекста.
Механизмы выступают в качестве связующего звена между двумя хранилищами. В графе они представлены в виде экономической идеи вместе с её источниками, а в учётной книге — в виде метки на каждой гипотезе и кандидате, использовавшем этот механизм. Эмпирические сводки могут быть отображены на узлах графа для удобства навигации, но это лишь отражения; настоящие данные хранятся в базе экспериментов. Поэтому хороший пакет контекстной информации формируется путём объединения данных из разных систем. Он включает небольшую соседнюю область графа, информацию о происхождении источников, текущие эмпирические сводки, недавние неудачи в определённых условиях и ограничения платформы. Модель не нуждается в полном графе или в каждой строке с данными PnL; важен лишь самый короткий путь доказательств к текущему решению.
Когда граф и реестр имеют одинаковый идентификатор механизма, становится возможным одновременно просматривать всю ветвь: теорию, эксперименты, все кандидатские решения, а также краткое описание на узле графа, соответствующем реестру. Идея авторизации выкупа взята непосредственно из статьи 1995 года, однако она так и не была привязана к ветке, связанной с обратной покупкой акций, поэтому никаких результатов, связанных с ней, невозможно получить из графа.
Стоило бы сделать несколько контрактов на передачу данных более строгими. Объекты, перемещаемые между хранилищами, должны содержать явно указанную версию схемы JSON. Любой вычисляемый показатель должен указывать версию кода, момент создания исходного кода и версию метода, который его вычислил. Каждый эксперимент требует наличия манифеста с адресным указанием содержимого для обеспечения воспроизводимости, в котором перечисляются коммит кода, сводная информация об окружении, настройки платформы, а также идентификаторы гипотезы и реализации. Кроме того, процедура согласования должна тестироваться так же, как и любая другая проблема качества данных, а не считаться чем-то безвредным второстепенным аспектом.
Если кратко описать подход к проектированию, то граф — это контекст, реестр — тоже контекст, а связь между ними также является контекстом. Эта связь требует такой же тщательной обработки, как и код модели.
Где это пересекается с инженерией Harness
Ни одна просьба не передаётся целиком в виде всего хранилища. Каждое хранилище добавляет небольшой фрагмент в типизированный пакет, и каждый специалист получает ровно то, что ему нужно. Результаты по типу возвращаются в соответствующие места, правила никогда не записываются туда, а два цикла заполняют следующий пакет с разной скоростью.
Это разделяет области инжиниринга контекста и инжиниринга механизмов обработки. Управление контекстом отвечает за уровни от L1 до L3: оно хранит источники данных, измерения, априорные знания, информацию о происхождении данных, временные метки, объем данных и стабильные идентификаторы. Уровень L4, представляющий собой агентный механизм обработки, определяет, какие доказательства следует извлекать, сколько данных допускается за пределами определенной стадии, к какому специалисту они передаются и какие выводы считаются обоснованными. Ниже находятся исходный код (уровень L5), локальная инфраструктура (уровень L6) и распределенная инфраструктура (уровень L7). Эти слои смогут безупречно выполнить неверное решение, но они не могут определить, был ли входной элемент правилом, наблюдением или убеждением.
Ранняя версия снизила четкость этого разделения. Основной файл инструкций превратился в вики из 627 строк, в котором смешивались правила турнира, информация о текущем статусе, методы и уроки предыдущего дня. После того как его сократили до небольшого роутера, контекст доходил до агента через четыре канала. Короткий слой оставался загруженным постоянно. Пакет запуска передавал свежие уроки и предупреждения. Правила, специфичные для определенной области, подключались только тогда, когда задача касалась этой области, а специалисты с их знаниями загружались по мере необходимости.
Одна запрос, прослеживаемый по всем каналам
Рассмотрим вопрос «Что следует попробовать дальше?» Система начинает с формирования пакета предполетной проверки. Из уровня L1 она берет соответствующие выражения, параметры настройки и ограничения по оценке. Из уровня L2 поступают информация о текущем наборе проектов, недавних измерениях, степени покрытия пространства поиска и результатах, которые ещё не решены. Из уровня L3 берутся наиболее релевантные ветви графа, теоретические основания, критерии опровержения, спецификации исследований и эмпирические выводы.
Затем вступают в действие подагенты. Специалист по гипотезам использует этот пакет для предложения нескольких экономических подходов, не скрывая слабости логики, лежащей в основе формул. После выбора одного из подходов специалист по моделированию берет зарегистрированную гипотезу и создает реализации, которые существенно отличаются друг от друга. Специалист по экспериментам получает дерево реализаций и ограничения платформы, затем фиксирует то, что подлежит измерению.
Каждый этап имеет свою цель. Слой L2 реестра получает сырые результаты платформы и нормализованные показатели. Операционные события, такие как запуск процессов, вызовы инструментов, попытки повтора и трафик для координации, хранятся в хранилище событий. Если результат позволяет сделать вывод или выявить фальсификатор в определённом диапазоне, он сохраняется в слое L3. Объединённые данные графа формируются путём сопоставления с реестром и никогда не редактируются вручную, в то время как большие серии данных о прибылях и убытках, графики и адаптированные модели превращаются в объекты, на которые ссылаются другие записи.
Оба предложенных варианта начинались с пакетов, уже содержащих необходимые данные. Одна группа ранее улучшила портфель, а другая идея использовала версию, которая уже дала несвязанные результаты. Идея с изменением рейтинга также получила пакет, непроверенную ячейку на карте возможностей, а также пример прошлого успеха для подражания, однако все 18 её вариантов всё равно провалились.
Этапирование инфраструктуры
Попытка переместить всё сразу будет ошибкой. Каждый канал меняется на своем этапе, и шлюз открывается только тогда, когда для этого есть осязаемый триггер. На правой стороне показан единственный надежный путь записи (commit, outbox, exporter, projection), в отличие от двойной записи, которая создает две противоречащие друг другу версии данных.
Текущая локальная стек-структура способна на большее, чем кажется. SQLite — отличный стандартт для одиночного исследователя: он обеспечивает настоящие транзакции, простую резервную копирование, быстрые локальные запросы и практически без накладных расходов на обработку. Однако существуют определенные ограничения. База данных объемом в несколько гигабайт содержит десятки миллионов строк временных рядов; несколько процессов могут конкурировать за право на локальную запись; количество событий во время работы постоянно растет; артефакты и снимки состояния базы привязаны к одной машине, а воспроизведение результата в другом месте требует гораздо большего количества скрытых данных, чем кто-либо хотел бы. Поэтому целесообразна пятиэтапная эволюция этой системы.
На этапе 0 делается акцент на приведении дизайна в соответствие с реальностью: либо завершается незавершённая миграция данных о PnL, либо она осознанно откатывается, после чего автоматизируется аудит, сравнивающий документацию с данными в реальном времени. На этапе 1 крупные файлы перемещаются во внешние хранилища, совместимые с S3: ежедневные данные о PnL, графики, файлы моделей, крупные отчёты и снимки базы данных хранятся там, причём данные о PnL разделяются на сжатые части в формате Parquet, подкреплённые неизменяемыми манифестами, контрольными суммами и правилами управления жизненным циклом. На этапе 2 метаданные перемещаются только тогда, когда конкурентность вынуждает это сделать. Когда удалённые сотрудники, несколько машин или коллеги должны записывать данные одновременно, журнал операций и хранилище событий переносятся в управляемую версию PostgreSQL — либо как отдельные базы данных, либо как отдельные схемы с собственными правилами хранения. На этапе 3 внедряются инструменты MLOps в качестве дополнения, но никогда не как источник истинных данных; таким образом, инструменты вроде Weights & Biases или MLflow могут помочь, не заменяя журнал операций или графовые структуры. На четвертом этапе оркестрация отделяется от состояния: исследователи работают в контейнерах с неизменяемыми манифестами задач, в то время как очередь или движок рабочих процессов распределяет идемпотентные задачи с механизмами аренды ресурсов, повторных попыток и таймаутов. На пятом этапе появляются более сложные инструменты анализа, но только тогда, когда объем работы этого требует. Формат таблиц lakehouse, специализированная графовая база данных или платформа потоковой обработки могут оказаться полезными в будущем, но лишь тогда, когда начинают возникать проблемы с определенными запросами, такими как сканирование миллиардов записей, множество одновременных просмотров графов, эволюция схемы в больших коллекциях в формате Parquet или потребление событий с низкой задержкой.
Нельзя приписать этой архитектуре точное улучшение производительности, поскольку ее влияние никогда не изолировали для анализа. Ее реальный вклад заключается в возможности для системы честно противоречить самой себе. Одна статья предлагает одно решение, симуляция — другое, инструменты проверки уточняют выводы, но правила турнира остаются прежними.
Связанные статьи
- Пять уровней структуры агентского харнеса, включая примеры кода, который не будет работать без них — практический обзор пяти мест, в которых агентский харнес применяет правила в коде, от границ выполнения до потоков контекста, а также того, что исследования могут и не могут доказать.
- Агенты, способные к самосовершенствованию через навыки: повторное использование, выбор, исправление и проверка — четырехэтапная концепция агентов, которые улучшают собственные навыки: сохранение рабочего кода, уточнение описаний, предложение проверенных исправлений и проверка результата перед передачей задачи.