# Факторы

Факторы – показатели релевантности документа, основанные на теле документа,
поисковом запросе, данных пользователя и др.

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

#### Документация SaaS
* [Формула релевантности и факторы](https://doc.yandex-team.ru/Search/saas/saas-overview/concepts/rank-gen.html?lang=ru)
* [Пользовательские факторы](https://wiki.yandex-team.ru/jandekspoisk/saas/factorsinfo/user/)

В Поиске есть факторы 4х типов:
1. Зонный фактор
2. Динамический фактор
3. Статический фактор
4. Пользовательский фактор

## Зонный фактор

Зонный фактор – фактор, основанный на том, насколько точно поисковый запрос попадает
в конкретную зону в документе. Предположим, что при поиске кандидатов в Фемиде
мы хотим выше поднимать кандидатов, у которых поисковый запрос сильно пересекается с контактами.
Тут нам и поможет зонный фактор по зоне `contacts`

## Динамический фактор

Динамические факторы похожи на зонные (тоже зависят от текста запроса и текста документа),
но они вычисляются исходя из всего документа, и мы особо никак не влияем на их вычисление.
Т.е., если на зоны мы разбиваем документ сами и выделяем зоны, по которым считать факторы,
то динамические факторы вообще автомагически считаются в SaaS.

## Статический фактор

Статический фактор – фактор, который задаётся явно при индексации. К примеру, при поиске людей на Стаффе
мы хотим, чтобы бывшие сотрудники были ниже действующих сотрудников. Для этого при индексации мы явно
задаём **статический фактор** "бывший сотрудник" и в дальнейшем учитываем его в нашей формуле ранжирования.

## Пользовательский фактор

Пользовательский фактор – это фактор, в вычислении которого используются данные пользователя
(например, его подразделение).

К примеру, если мы хотим при поиске людей на Стаффе поднимать выше людей из твоего подразделения,
нам сначала нужно каждого человека, попадающего под поисковый запрос,
разметить флагами "входит в твоё подразделение".
Эти флаги – есть пользовательские факторы.

## Заведение нового фактора

Все факторы из-за своей специфики задаются немного по-разному:
- Зонные и динамические факторы вычисляются автоматически на основе поиск.запроса и тела/зон документа.
- Статические факторы задаются в момент индексации.
- Пользовательские факторы задаются в момент обработки поискового запроса на основе самого поиск.запроса,
атрибутов документа и каких-то дополнительных данных о текущем пользователе.

Все факторы должны быть явно прописаны в конфиге SaaS. У нас в этом месте полуавтомат:
есть management-команда для формирования конфига, который потом нужно явно прописать в их админке.

#### Пример

В качестве примера возьмём поиск по людям на Стаффе. Предположим, что нам нужно завести
новый пользовательский фактор `is_me`, который позволит повысить в выдаче самого пользователя.
Например, если пользователь с логином @dezmound вбивает в саджесте по людям `dez`,
он с высокой вероятностью ищет самого себя. Тут нам и поможет фактор `is_me`

Что нам нужно для этого сделать:
1. В yaml-конфигах `settings.isearch.yaml` задаём для `people` наш фактор.
Для этого в `searches.base.people.factors.user` прописываем `is_me`.
Заметье, что мы используем `user`, потому что это пользовательский фактор – там рядом также есть `zone` и `static`.
Динамические факторы задаются немного по-другому – для этого есть глобальная настройка
`dynamic_factors` в `settings.default.yaml`
2. Генерим конфиг для SaaS, запустив команду `isearch relev_config intrasearch-people`. На выходе получаем json.
3. Переходим в [админку SaaS](https://saas-mon.n.yandex-team.ru/service_info?service=intrasearch-people&ctype=stable)
4. Среди конфигов выбираем `relev.conf-intrasearch-people`.
5. Вставляем в форму json, полученный в п.2. Сохраняем, деплоим (сначала на prestable)

В случае с польз.факторами, их ещё нужно явно вычислять в момент поиск.запроса.
Как именно это делается, можно посмотреть на примерах метода
`apply_user_factors` [здесь](../abovemeta/request_builders.py)
