nBest
При совместном использовании в одном сценарии нескольких типов правил активации они срабатывают в порядке убывания приоритета:
- Паттерны.
- Примеры и группы примеров.
- Интенты.
В сценариях со сложным механизмом выбора правил активации для перехода в стейт вы можете получить доступ к наиболее вероятным правилам из любого места сценария через $context.nBest.
Конфигурационный файл
Чтобы включить заполнение $context.nBest, в конфигурационный файл chatbot.yaml нужно добавить следующий раздел:
nlp:
nbest: 3В значении параметра nlp.nbest укажите необходимое число правил, к которым нужно иметь доступ из сценария.
Содержимое массива
После настройки конфигурационного файла в объекте $context, представляющем собой текущий контекст обработки запроса, становится доступно поле nBest.
В значении $context.nBest содержится массив из nlp.nbest объектов, представляющих собой наиболее вероятные правила для перехода в какой-либо стейт.
Объект на первом месте в массиве $context.nBest отбирается в зависимости от того, задан ли в сценарии собственный механизм выбора правил активации через обработчик selectNLUResult:
- Если обработчик задан, то на первом месте
$context.nBestвсегда идет правило, которое было записано обработчиком в поле$context.nluResults.selected. - Если не задан, то на первом месте расположено правило, по которому произошел переход в целевой стейт, с учетом стандартного приоритета в порядке от паттернов к примерам и интентам.
Правила на втором и последующих местах отсортированы по убыванию значения score.
Таким образом, вес правила на втором месте может оказаться выше, чем на первом.
Сценарий
Без обработчика selectNLUResult
Рассмотрим простой сценарий, в котором используются все типы правил активации. Интент /привет предварительно обучен на тренировочной фразе привет:
init:
bind("postProcess", function($context) {
log($context.nBest);
});
theme: /
state: Pattern
q!: привет
state: Example
e!: привет
state: Intent
intent!: /приветВ блоке init настроен обработчик postProcess, который после каждого запроса логирует содержимое $context.nBest. При запросе привет в лог запишется следующий массив:
[
// Первый объект — правило для перехода по паттерну
{
"clazz": "/Pattern", // Класс, в который изначально попал запрос
"score": 0.79, // Вес, с которым сработало правило
"pt": {
// Алиас для поля `parseTree`
},
"debugInfo": {
// Служебная информация о сработавшем правиле
},
"ruleType": "pattern", // Тип сработавшего правила
"parseTree": {
// Полное дерево разбора запроса
},
"targetState": "/Pattern", // Стейт, в который произошел переход
},
// Второй объект — правило для перехода по интенту
{
"clazz": "/Intent",
"score": 1,
"pt": {
// ...
},
"debugInfo": {
// ...
},
"ruleType": "intent",
"parseTree": {
// ...
},
"targetState": "/Intent"
},
// Третий объект — правило для перехода по примеру
{
"clazz": "/Example",
"score": 0.6069870970795817,
"pt": {
// ...
},
"debugInfo": {
// ...
},
"ruleType": "example",
"pattern": "привет",
"parseTree": {
// ...
},
"targetState": "/Example"
}
]С обработчиком selectNLUResult
Добавим в блок init обработчик, который переопределяет порядок срабатывания правил активации так, чтобы наибольший приоритет был у примеров:
bind("selectNLUResult", function($context) {
if ($context.nluResults.examples.length > 0) {
$context.nluResults.selected = $context.nluResults.examples[0];
return;
}
if ($context.nluResults.patterns.length > 0) {
$context.nluResults.selected = $context.nluResults.patterns[0];
return;
}
if ($context.nluResults.intents.length > 0) {
$context.nluResults.selected = $context.nluResults.intents[0];
}
});Теперь, если повторить предыдущий запрос, порядок объектов в массиве $context.nBest изменится:
[
{
"clazz": "/Example",
"score": 0.6069870970795817
// ...
},
{
"clazz": "/Intent",
"score": 1
// ...
},
{
"clazz": "/Pattern",
"score": 0.79
// ...
}
]