Relevance-Guided Residual Calibration (RRC) — это метод постобработки эмбеддингов, уже сжатых спектральным способом. Он уточняет веса сжатых направлений по небольшому набору релевантностных суждений и встраивает поправки в существующее преобразование, не требуя переобучения энкодера или дополнительной стадии вывода. Авторы описывают процедуру в препринте arXiv:2610.37707; ниже воспроизведены заявленные ими шаги, а не результат нашего запуска.
Что такое RRC и когда его применять
Спектральное сжатие уменьшает затраты на хранение и подсчёт близости в dense retrieval, проецируя эмбеддинги на меньшее главное подпространство. Проблема, которую решает RRC: веса компрессора выводятся из корпуса и привязывают все сохранённые направления к общему спектральному тренду, не учитывая вклад каждого направления в релевантность.
RRC оценивает маржинальные веса по средним и дисперсиям разностей вкладов положительных и отрицательных пар вдоль каждого сохранённого направления. Затем он оставляет направления с положительной оценкой веса, раскладывает их лог-веса на степенной тренд и остаток и добавляет остаток к лог-весам компрессора. Метод применим к PCA, Whitening и SpecTemp.
Применять RRC имеет смысл, когда у вас уже есть сжатые эмбеддинги и небольшой набор суждений о релевантности, но нет вычислительных ресурсов или данных для переобучения энкодера. Поправки встраиваются в преобразование, общее для документов и запросов, поэтому дополнительного прохода вывода не появляется.
Что нужно подготовить до калибровки
Для воспроизведения процедуры понадобятся четыре вещи. Во-первых, уже обученный спектральный компрессор — PCA, Whitening или SpecTemp — вместе с его матрицей преобразования и лог-весами направлений. Во-вторых, сжатые эмбеддинги запросов и документов, к которым применялось это преобразование. В-третьих, набор положительных и отрицательных пар «запрос — документ» с релевантностными суждениями. В-четвёртых, среда с numpy для матричных операций и подгонки степенного тренда.
Авторы не фиксируют в полученной странице препринта минимальный размер набора суждений. Поскольку веса оцениваются по средним и дисперсиям, для расчёта нужны и положительные, и отрицательные пары, а их количество должно быть достаточным, чтобы оценка не сводилась к шуму.
Шаг 1. Собрать положительные и отрицательные пары
Сформируйте две выборки. Положительная пара — запрос и документ, отмеченный как релевантный. Отрицательная — тот же запрос и документ, отмеченный как нерелевантный. Для оценки среднего и дисперсии нужны оба типа пар; конкретный минимум авторы не задают.
Для каждой пары получите сжатые векторы запроса и документа тем же преобразованием, которое вы собираетесь калибровать. RRC не меняет способ проецирования: он корректирует веса уже сжатых направлений.
Шаг 2. Рассчитать маржинальные веса направлений

Для каждого направления j и каждой положительной пары вычислите вклад направления в сходство запроса и документа — произведение j-х координат сжатых векторов. То же сделайте для отрицательных пар. Затем для направления j найдите разности вкладов положительных и отрицательных пар.
Оценка веса направления строится по среднему и дисперсии этих разностей. Направление считается полезным для релевантности, если его оценённый вес положителен. Если оценка неположительна, направление не даёт маржинального выигрыша и отбрасывается.
Ниже — numpy-реализация описанной процедуры. Массивы Q_pos, D_pos, Q_neg, D_neg содержат сжатые векторы запросов и документов для положительных и отрицательных пар; scale — нормировка знаменателя, точное значение которой сверяйте с полным текстом препринта.
import numpy as np
# Вклад направления j в сходство пары: покоординатное произведение.
pos_contrib = Q_pos * D_pos # форма (n_pos, d)
neg_contrib = Q_neg * D_neg # форма (n_neg, d)
# Разности вкладов положительных и отрицательных пар по каждому направлению.
# Для парного вычитания нужны совпадающие размеры; при разном числе пар
# используйте средние значения или выровняйте выборки.
mu = pos_contrib.mean(axis=0) - neg_contrib.mean(axis=0)
var = pos_contrib.var(axis=0) + neg_contrib.var(axis=0)
# Маржинальный вес: положительная средняя разность, нормированная на разброс.
weight = mu / np.sqrt(var + 1e-12)
# Направления с положительным оценённым весом остаются в носителе.
support = weight > 0
Итог шага — булев массив support, который отмечает направления с положительным маржинальным весом. Это прямой перевод заявленной авторами операции «means and variances of positive–negative score contributions», а не выполненный нами запуск на данных.
Шаг 3. Разделить тренд и остаток, получить новые веса

Оставьте только направления с положительным оценённым весом. Для их лог-весов подгоните степенной тренд — зависимость лог-веса от номера направления в порядке убывания собственного значения. Тренд описывает общую спектральную форму, унаследованную от компрессора.
Вычтите подогнанный тренд из лог-весов и получите остаток. Затем добавьте этот остаток к исходным лог-весам компрессора на отобранном множестве направлений. Так релевантностные суждения корректируют отдельные направления, а общий спектральный тренд компрессора сохраняется.
# log_w — исходные лог-веса компрессора для направлений из support.
idx = np.arange(len(log_w))
# Подгонка степенного тренда log_w ~ a * idx**b в лог-пространстве.
coeff = np.polyfit(np.log(idx + 1), log_w, 1)
trend = coeff[0] * np.log(idx + 1) + coeff[1]
# Остаток и калиброванные лог-веса: добавление остатка к исходным весам.
residual = log_w - trend
calibrated_log_w = log_w + residual
Здесь trend — значения подобранной степенной зависимости, а не константа. После сложения calibrated_log_w = 2 * log_w - trend.
Шаг 4. Применить калиброванное преобразование к запросам и документам
Соберите обновлённые веса: для направлений из support возьмите calibrated_log_w, для остальных направлений — нулевой вес. Примените преобразование к сжатым векторам запросов и документов, умножив координаты отобранных направлений на exp(calibrated_log_w) и обнулив отброшенные координаты.
# calibrated_weight — итоговые веса направлений после калибровки.
scale_vector = np.zeros(d)
scale_vector[support] = np.exp(calibrated_log_w)
# Применение калиброванного преобразования к уже сжатым векторам.
Q_cal = Q * scale_vector
D_cal = D * scale_vector
Поскольку поправка встроена в преобразование, общее для обеих сторон, на этапе вывода дополнительных вычислений не требуется: вы используете новые веса при масштабировании координат.
Шаг 5. Проверить результат на оценке
Сравните качество поиска до и после калибровки на отложенном наборе запросов. Используйте метрику nDCG@10 или ту, которая принята в вашей задаче. Отложенный набор не должен пересекаться с парами, по которым оценивались веса, иначе оценка будет завышена.
Авторы сообщают, что на пяти оценённых наборах BRIGHT SpecTemp+RRC улучшает SpecTemp в среднем на 2,34 пункта nDCG@10 при 768 измерениях. Это заявленный результат производителя метода, а не наш независимый замер; на ваших данных прирост может отличаться.
Характерные ошибки и как их исправить
Все направления получили неположительный вес. Вероятная причина — слишком малый набор пар или отрицательные документы, которые слабо отличаются от положительных по вкладу направлений. Добавьте больше отрицательных пар и проверьте, что положительные и отрицательные документы действительно различаются по релевантности.
После калибровки метрика упала. Проверьте, не использовались ли пары из оценочного набора при расчёте весов. Если утечки нет, вероятно, набор суждений слишком мал или смещён относительно целевого распределения запросов. Соберите более репрезентативные пары и повторите оценку.
Остаток доминирует над трендом. Если подгонка степенного тренда неустойчива, лог-веса после калибровки могут сильно отклониться от исходного масштаба. Проверьте подгонку тренда и ограничьте величину поправки, если отклонение выходит за ожидаемый диапазон.
Ограничения метода и заявленные результаты
Источник — препринт авторов метода, а не независимая рецензия. Мы не запускали код и не проверяли воспроизводимость на собственных данных. Ссылка на код в аннотации ведёт на анонимный репозиторий, доступность которого не подтверждена.
Авторы заявляют, что SpecTemp+RRC достигает наивысшей средней эффективности среди протестированных компрессоров на группе BEIR и на BRIGHT при каждой целевой размерности. На пяти оценённых наборах BRIGHT при 768 измерениях средний прирост к SpecTemp составляет 2,34 пункта nDCG@10. Выигрыш, по заявлению авторов, сохраняется при скалярном и продуктовом квантовании, улучшая соотношение между объёмом хранения на документ и качеством поиска. Это результаты из препринта, и их стоит проверять на собственных данных.


