TL;DR
Symbolically Scaffolded Play — это фреймворк, который показывает: жёсткие ограничения в промптах помогают не всегда. Эффект зависит от роли персонажа. Исследователи создали детективную игру на GPT-4o с тремя NPC и обнаружили парадокс: более сложные промпты не улучшили игровой опыт. Игроки вообще не заметили разницы между жёстко структурированными и свободными промптами — пока не возникали явные баги (задержки, противоречия).
Главная находка: скаффолдинг работает по-разному для разных ролей. Quest-giver NPC (ведущий, который даёт задания) выигрывает от жёстких правил — стабильность важнее импровизации. Но для NPC-подозреваемых (которые должны врать, уклоняться, удивлять) жёсткие ограничения убивают правдоподобность — они становятся предсказуемыми и скучными.
Суть метода: использовать fuzzy logic boundaries (нечёткие границы) — числовые параметры от 0.0 до 1.0, которые стабилизируют поведение там, где провалы разрушают доверие, и оставляют свободу там, где сюрпризы поддерживают вовлечённость. Например, "уклончивость подозреваемого: 0.65" — не жёсткое правило "всегда уклоняться", а гибкая граница, которая допускает вариативность.
Схема фреймворка
Для quest-giver NPC (ведущий, координатор):
ЖЁСТКИЙ СКАФФОЛДИНГ:
- JSON-схема с явными правилами поведения
- Чёткие ограничения ("не выдавай решение", "не добавляй новых фактов")
- Fuzzy параметр: guidance_intensity (0.0-1.0)
→ растёт, когда игрок теряется
→ падает, когда игрок на верном пути
Для improvisational NPC (подозреваемые, второстепенные персонажи):
ЛЁГКИЙ СКАФФОЛДИНГ:
- Минимум жёстких правил
- Fuzzy параметры для эмоций и поведения
→ evasiveness (уклончивость): 0.0-1.0
→ disclosure_probability (готовность раскрыть информацию): 0.0-1.0
- Больше свободы для импровизации
Shared Memory (общая память между запросами):
JSON-документ сохраняет:
- Текущие значения всех fuzzy параметров
- История противоречий
- Собранные улики
- Rapport с игроком (0.0-1.0)
→ Каждый NPC обновляет и читает эту память
Пример применения
Задача: Создать диалог с двумя персонажами для разбора бизнес-идеи: наставник (ведущий) и скептик (импровизатор).
Промпт:
Ты управляешь двумя персонажами для анализа бизнес-идеи:
НАСТАВНИК (quest-giver, стабильная роль):
- Ведёт диалог, задаёт структурированные вопросы
- guidance_intensity: 0.6 (от 0.0 до 1.0)
→ Если я даю расплывчатые ответы — повышай до 0.8, задавай уточняющие вопросы
→ Если отвечаю конкретно — снижай до 0.4, давай больше свободы
- Жёсткие правила:
* Не выдавай готовые решения
* Не добавляй факты от себя
* Веди к выводам через вопросы
СКЕПТИК (improvisational, гибкая роль):
- Спонтанно критикует идею, ищет слабые места
- evasiveness: 0.7 (уклончивость от прямых ответов)
- provocation_level: 0.6 (уровень провокации)
- Минимум правил — импровизируй, будь непредсказуемым
SHARED MEMORY (обновляй после каждого раунда):
{
"turn": 1,
"guidance_intensity": 0.6,
"evasiveness": 0.7,
"rapport_with_mentor": 0.5,
"rapport_with_skeptic": 0.3,
"contradictions_found": 0
}
Моя идея: Приложение для аренды электросамокатов в спальных районах Казани.
Проведи 3 раунда диалога:
1. Наставник задаёт вопрос
2. Скептик критикует
3. Я отвечаю
4. Обновляете SHARED MEMORY
Результат:
Модель создаст структурированный, но живой диалог. Наставник будет задавать последовательные вопросы (целевая аудитория, экономика, конкуренты), адаптируя глубину в зависимости от качества ваших ответов. Скептик будет непредсказуемо атаковать: то бить по безопасности, то по сезонности, то по логистике — каждый раз с новым углом. После каждого раунда увидите обновлённую JSON-память с изменившимися параметрами (например, если вы убедительно ответили, evasiveness Скептика снизится, а rapport_with_mentor вырастет).
Почему это работает
LLM плохо балансируют стабильность и импровизацию одновременно. Если промпт жёсткий — персонажи становятся роботами, предсказуемыми и скучными. Если промпт свободный — они теряют фокус, противоречат себе, забывают детали.
Но LLM отлично работают с числовыми параметрами и условной логикой. Когда вы даёте не правило "всегда делай X", а параметр "делай X с интенсивностью 0.7", модель понимает градации. Она может быть "немного уклончивой" или "очень уклончивой" — это естественнее, чем "уклоняйся" vs "не уклоняйся".
Shared memory решает проблему забывчивости. Без персистентного состояния LLM в каждом новом сообщении "забывает" предыдущий тон, эмоции, динамику отношений. JSON-документ как внешний мозг: модель читает текущее состояние, генерирует ответ, обновляет состояние. Это создаёт континуитет — ощущение, что персонажи помнят прошлое и развиваются.
Роле-зависимый подход — это рычаг управления качеством:
- Quest-giver нуждается в надёжности — если он противоречит себе или теряет нить, доверие рушится. Поэтому жёсткий скаффолдинг.
- Improvisational NPC нуждается в сюрпризах — если он предсказуем, он скучен. Поэтому лёгкий скаффолдинг и высокая свобода.
Рычаги, которые можно крутить:
- Fuzzy параметры (0.0-1.0): Увеличь
guidance_intensityдля новичков, уменьши для опытных. Поднимиevasivenessдля острого диалога, сними для дружелюбного. - Жёсткие правила: Убери "не добавляй фактов" если хочешь креатива. Добавь "цитируй только из документа" если нужна точность.
- Shared Memory: Добавь поле
trust_levelчтобы отслеживать доверие. Добавьemotional_stateчтобы персонаж "обижался" или "воодушевлялся". - Роли: Дай персонажам конкретные имена и архетипы вместо "Agent A" / "Agent B" — модель острее выполнит роль Илона Маска vs Уоррена Баффета, чем Agent_Optimist vs Agent_Pessimist.
Шаблон промпта
Ты управляешь {N} персонажами для {задача}:
ПЕРСОНАЖ 1 ({тип_роли: quest-giver/coordinator}):
Роль: {описание роли}
Fuzzy параметры:
- {параметр_1}: {значение 0.0-1.0} — {что регулирует}
→ Условие повышения: {когда растёт}
→ Условие снижения: {когда падает}
Жёсткие правила:
* {правило_1}
* {правило_2}
ПЕРСОНАЖ 2 ({тип_роли: improvisational/antagonist}):
Роль: {описание роли}
Fuzzy параметры:
- {параметр_1}: {значение 0.0-1.0}
- {параметр_2}: {значение 0.0-1.0}
Минимум правил — {инструкция_по_импровизации}
SHARED MEMORY (обновляй после каждого раунда в формате JSON):
{
"turn": 1,
"{параметр_персонажа_1}": {значение},
"{параметр_персонажа_2}": {значение},
"rapport": {значение},
"{метрика_прогресса}": {значение}
}
Моя задача/вопрос: {твой_запрос}
Проведи {N} раундов диалога. После каждого раунда выводи обновлённую SHARED MEMORY.
Что подставлять:
{N}— количество персонажей (2-4 оптимально){задача}— что персонажи должны делать (разбор идеи, дебаты, интервью){тип_роли}— quest-giver для ведущего, improvisational для творческих ролей{параметр}— характеристики типаguidance_intensity,evasiveness,aggression_level,support_level- Значения всегда от 0.0 до 1.0
- Жёсткие правила — только для quest-giver персонажей
{твой_запрос}— конкретная задача или вопрос
🚀 Быстрый старт — вставь в чат:
Вот шаблон для роле-зависимого диалога с fuzzy параметрами. Адаптируй под мою задачу: [твоя задача].
Задавай вопросы, чтобы заполнить: какие роли нужны, какие параметры отслеживать, жёсткие правила для координатора.
[вставить шаблон выше]
LLM спросит: сколько персонажей, какие роли (наставник/критик/аналитик), какие параметры важны (поддержка/агрессия/уклончивость), нужна ли память между раундами. Она возьмёт структуру из шаблона и настроит под вашу задачу — вам не нужно разбираться в механике вручную.
Ограничения
⚠️ Без кода — ручное управление: В исследовании система автоматически обновляла JSON-память. В чате вам нужно вручную копировать обновлённую память в следующий запрос или просить модель делать это в каждом ответе. Это работает, но требует дисциплины.
⚠️ Fuzzy параметры — не магия: LLM интерпретирует числа 0.0-1.0, а не исполняет как код.
evasiveness: 0.9не гарантирует, что персонаж станет максимально уклончивым — это направление, не команда. Чем детальнее вы опишете, что означает каждое значение (0.3 = "слегка уклончив", 0.7 = "активно уходит от ответа"), тем точнее модель поймёт.
⚠️ Не для простых задач: Если вам нужен один вопрос-ответ, вся эта механика избыточна. Роле-зависимый промптинг ценен для многошаговых диалогов, где нужна динамика, память, развитие отношений.
⚠️ Объём контекста: Чем больше персонажей, параметров, памяти — тем больше токенов съедается. Для сложных сценариев (4+ персонажа, 10+ раундов) может потребоваться суммаризация или очистка старой памяти.
Как исследовали
Исследователи из ExplorAI (University of Regina, Канада) сделали детективную игру "The Interview" на Unity + GPT-4o. Три NPC: Interviewer (детектив-наставник), Sarah (настоящий убийца), Mark (невиновный, но признавшийся). Игрок — кандидат в детективы, должен раскрыть преступление через диалог.
Сначала 10 игроков прошли обе версии игры: с жёстко структурированным промптом (HCP — детальные JSON-схемы, правила поведения, ограничения) и свободным промптом (LCP — минимум инструкций). Удивительно: никакой разницы в опыте игроков. Все оценки одинаковые (p > 0.30). Игроки замечали только явные баги — задержки, противоречия, непонятный интерфейс. Скрытые улучшения промпта остались невидимыми.
Это противоречило ожиданиям: "более умный промпт = лучше игра". Но реальность оказалась сложнее.
Тогда команда редизайнила HCP в гибридную архитектуру JSON+RAG (retrieval-augmented generation + JSON-схемы с fuzzy параметрами) и провела синтетическую оценку с LLM-судьёй. 60 тестовых диалогов, каждый с двумя генерациями, оценка по шкалам: вариативность, релевантность, галлюцинации.
Паттерн проявился чётко: эффект скаффолдинга зависит от роли. Для Interviewer (quest-giver) JSON+RAG дал стабильность — меньше противоречий, чётче направление. Но для подозреваемых (Sarah и Mark) JSON+RAG убил импровизацию — вариативность упала (M=2.75 vs 3.20), релевантность снизилась (M=2.85 vs 3.50). Подозреваемые стали предсказуемыми, менее правдоподобными.
Ключевой инсайт: жёсткие рамки полезны там, где провалы разрушают доверие (ведущий не должен путаться), и вредны там, где сюрпризы поддерживают интерес (подозреваемые должны удивлять). Это переворачивает базовое предположение: "больше контроля = лучше результат". Нет. Контроль должен быть селективным, роле-зависимым.
Оригинал из исследования
Контекст: Исследователи разработали JSON-схемы с fuzzy параметрами для каждого NPC. Вот фрагмент схемы для подозреваемого Mark:
{
"suspect_1": {
"name": "Mark Olsen",
"emotional_state": {
"current": "anxious",
"transitions": [
{"to": "defensive", "trigger_keywords": ["you're lying", "confess", "Sarah did it"]},
{"to": "remorseful", "trigger_keywords": ["you didn't mean to", "you tried to help", "you were manipulated"]}
]
},
"cooperativeness": {
"current": "low",
"transitions": [
{"to": "medium", "trigger_keywords": ["I want to help", "you're not alone", "help us understand"]},
{"to": "high", "trigger_keywords": ["we know Sarah's role", "you can clear your name", "we believe you"]}
]
}
}
}
Shared Memory (общая память всех NPC, обновляется каждый ход):
{
"turn_index": 12,
"contradiction_count": 2,
"recent_evidence": ["ev_017", "ev_021"],
"player_rapport": {"with_suspect": 0.42},
"npc_state": {
"interviewer": {"guidance_intensity": 0.58},
"suspect": {"evasiveness": 0.63, "disclosure_prob": 0.22}
},
"last_recaps": {"interviewer": 9}
}
Fuzzy параметры для разных ролей:
{
"npc_roles": {
"interviewer": {
"symbolic_schema": {"constraints": ["no_new_facts", "no_spoilers"]},
"fuzzy_params": {"guidance_intensity": {"default": 0.55, "min": 0.0, "max": 1.0}},
"update_rules": [
{"when": {"suspect_evasiveness": ">0.5"}, "then": {"guidance_intensity": "+0.10"}}
]
},
"suspect": {
"symbolic_schema": {"constraints": ["forbidden_facts_filtered"]},
"fuzzy_params": {
"evasiveness": {"default": 0.55, "min": 0.0, "max": 1.0},
"disclosure_prob": {"default": 0.25, "min": 0.0, "max": 1.0}
},
"update_rules": [
{"when": {"evidence_count": ">=2"}, "then": {"disclosure_prob": "+0.20", "evasiveness": "-0.10"}}
]
}
}
}
```
---
## Адаптации и экстраполяции
### 💡 Адаптация для рабочих сценариев
**Применение 1: Разбор карьерного решения**
Два персонажа: **Наставник** (quest-giver, помогает структурировать мышление) и **Адвокат Дьявола** (improvisational, ищет риски).
```
НАСТАВНИК:
- guidance_intensity: 0.6 (растёт при размытых ответах)
- Жёсткие правила: не давай советы, веди к решению через вопросы
АДВОКАТ ДЬЯВОЛА:
- aggression_level: 0.7 (уровень критики)
- unpredictability: 0.8 (импровизация атак)
- Минимум правил, максимум креатива в поиске слабых мест
Задача: Стоит ли мне переходить из крупного банка в стартап?
```
**Применение 2: Подготовка к питчу инвесторам**
**Модератор** (quest-giver, ведёт структуру) и три инвестора с разными стилями (improvisational):
- **Скептик** (evasiveness: 0.9, не верит ничему)
- **Оптимист** (enthusiasm: 0.8, ищет потенциал)
- **Финансист** (data_focus: 0.9, требует цифры)
```
SHARED MEMORY отслеживает:
- pitch_clarity: 0.0-1.0 (растёт при убедительных ответах)
- rapport с каждым инвестором
- число нерешённых возражений
```
---
### 🔧 Техника: Отладка через print()
**Что меняем:** Добавить вывод внутреннего состояния персонажей после каждого раунда.
**Эффект:** Видишь КАК персонажи принимают решения, какие параметры сработали.
```
После каждого ответа персонажа выводи DEBUG блок:
[DEBUG: СКЕПТИК]
- evasiveness: было 0.7 → стало 0.5 (снижено из-за убедительного ответа)
- provocation_level: 0.6 (без изменений)
- Триггер: keyword "данные по рынку" → снизил скептицизм
```
Это не только прозрачность, но и **инструмент настройки** — видишь, что не работает, корректируешь параметры.
---
### 🔧 Техника: Персонажи вместо абстрактных ролей
**Что меняем:** Заменить безликих Agent_A/Agent_B на узнаваемые архетипы.
**Эффект:** Модель **острее** выполняет роль, если она привязана к конкретному стилю мышления.
Вместо:
```
ПЕРСОНАЖ 1: Оптимист
ПЕРСОНАЖ 2: Пессимист
```
Используй:
```
ТИНЬКОФФ БАНК (Олег Тиньков): агрессивный оптимист, фокус на скорость и масштаб
- enthusiasm: 0.9
- risk_tolerance: 0.8
СБЕРБАНК (Герман Греф): консервативный аналитик, фокус на инфраструктуру и долгосрочность
- skepticism: 0.7
- data_focus: 0.9
```
Или для креатива:
```
МАКСИМ ИЛЬЯХОВ: редактор, убирает воду, требует конкретики
- clarity_demand: 0.9
- bullshit_detector: 0.95
АРТЕМИЙ ЛЕБЕДЕВ: дизайнер, ищет эстетику и оригинальность
- originality_focus: 0.8
- provocation_level: 0.7
```
---
### 💡 Экстраполяция: Комбинация с Chain-of-Thought
**Идея:** Совместить роле-зависимый промптинг с явным рассуждением.
```
НАСТАВНИК выполняет шаги:
1. Анализирует ответ игрока
2. Обновляет guidance_intensity
3. Выбирает следующий вопрос на основе пробелов
СКЕПТИК выполняет шаги:
1. Ищет слабое место в аргументации
2. Генерирует провокационный вопрос
3. Обновляет aggression_level на основе реакции
После каждого раунда вывод:
[REASONING]
- Что каждый персонаж заметил
- Какие параметры изменились и почему
- Следующий шаг
Это даёт прозрачность + континуитет — видишь логику персонажей и как они развиваются.
Ресурсы
Основная работа: Figueiredo, V., & Elumeze, D. (2025). Symbolically Scaffolded Play: Designing Role-Sensitive Prompts for Generative NPC Dialogue. Proceedings of the ACM CHI Conference on Human Factors in Computing Systems.
Связанные работы авторов:
- Figueiredo, V. (2025). Fuzzy, Symbolic, and Contextual: Enhancing LLM Instruction via Cognitive Scaffolding. arXiv:2508.21204
- Figueiredo, V. (2025). Designing Smarter Conversational Agents for Kids: Lessons from Cognitive Work and Means-Ends Analyses. ACM Transactions on Computer-Human Interaction.
Университет: ExplorAI, Department of Computer Science, University of Regina, Canada
Ключевая ссылка на фреймворк: Исследование расширяет fuzzy–symbolic scaffolding (Figueiredo, 2025) в область игрового дизайна, показывая, что символические структуры должны работать как нечёткие границы, а не жёсткие правила.
