TL;DR
Когда ты вставляешь в чат текст из PDF, OCR или скрейпинга — слегка искажённый текст опаснее, чем полностью нечитаемый. Это контринтуитивно, но задокументировано: с ростом количества случайных пробелов внутри слов точность LLM сначала падает, достигает дна, а потом — при почти полном разрушении слов — частично восстанавливается. Умеренный OCR-мусор оказывается в самой опасной зоне.
Исследователи назвали это Text Uncanny Valley — по аналогии с роботами из "Зловещей долины": робот, который почти человек, вызывает отвращение сильнее, чем явно механическая кукла. Текст, который почти нормальный, вводит модель в хаос сильнее, чем полностью разобранный по буквам. Причина: LLM переключается между двумя режимами обработки — пословным (нормальный текст) и побуквенным (полный хаос). А вот в середине — ни то ни другое не работает стабильно.
Практический вывод: если ты работаешь с текстом из PDF, сканов, веб-скрейпинга — не надейся, что "почти нормальный" текст пройдёт незаметно. Либо чисти до конца, либо предупреждай модель и используй двухшаговый подход: сначала восстановить слова, потом выполнять задачу.
Схема явления
Уровень искажения текста:
НОРМАЛЬНЫЙ (0%) → точность высокая
↓
ЛЁГКОЕ (10-20%) → начинает падать
↓
УМЕРЕННОЕ (30-50%) → ДНО (хуже всего) ← здесь живёт OCR-мусор
↓
СИЛЬНОЕ (70-80%) → всё ещё плохо
↓
ПОЛНЫЙ ХАОС (100%) → частично восстанавливается
Задача с corrupted текстом:
ШАГ 1: очистка текста → восстановленные слова (отдельный запрос)
ШАГ 2: основная задача → результат на чистом тексте
Оба шага выполняются через отдельные запросы в чате.
Пример применения
Задача: Ты получил от юриста договор аренды, вытащенный из скана через OCR. Нужно проверить ключевые условия: срок, цену, штрафные санкции. Текст выглядит примерно нормально, но кое-где слова "рассыпаны": "аренд атор", "обяза тельств", "рас торжени я".
Промпт (шаг 1 — очистка):
У меня текст из OCR-распознавания скана документа.
В нём местами слова разбиты случайными пробелами внутри —
например: "аренд атор", "обяза тельств", "рас торжения".
Восстанови все разбитые слова. Правило:
если пробел стоит внутри слова (нет смысла делить) — убери его.
Другое форматирование не трогай.
Выведи только исправленный текст, без комментариев.
Текст:
[вставить текст договора]
Промпт (шаг 2 — анализ на очищенном тексте):
Проанализируй этот договор аренды. Выдели:
1. Срок аренды
2. Размер арендной платы и порядок изменения
3. Условия досрочного расторжения и штрафы
4. Красные флаги — условия, которые невыгодны арендатору
[вставить очищенный текст из шага 1]
Результат: На шаге 1 модель вернёт текст с восстановленными словами. На шаге 2 — структурированный анализ с конкретными пунктами договора. Без очистки та же модель могла бы неверно процитировать условия, пропустить пункты или "не увидеть" ключевые формулировки — и при этом ответить уверенно, как будто всё нормально.
Почему это работает (и почему проблема не очевидна)
Почему LLM ломается на "почти нормальном" тексте. Модели разбивают слова на части (токены) перед обработкой. "Международный" → один-два токена. "Меж ду народ ный" → восемь токенов. При умеренном искажении словарь модели становится максимально хаотичным: часть слов целые, часть разбита по-разному. Это пик неразберихи — модель не может устоявшимся способом сопоставлять слова с их смыслом.
Два режима обработки и провал между ними. При нормальном тексте LLM работает пословно — распознаёт токены как знакомые единицы. При полном разрушении ("м е ж д у н а р о д н ы й") переключается в побуквенный режим — читает символ за символом, как шифр. Оба режима дают стабильный (пусть и разный) результат. Беда — в зоне между ними: модель не может выбрать режим и ошибается сильнее, чем в крайних случаях.
Что это значит на практике. Привычные OCR-артефакты — "не очень плохой" текст с 20-40% искажений — это именно дно кривой. Пользователь видит "читаемый" текст, отправляет в чат и получает уверенный, но неточный ответ. Это опаснее явного мусора: на явном мусоре видно, что что-то не так, а здесь всё выглядит нормально.
Рычаги управления:
- Провери источник текста перед вставкой — PDF через Ctrl+C, OCR, веб-скрейпинг = зона риска
- Двухшаговый промпт (очистка → задача) снижает риск
- Попроси модель сначала пересказать текст своими словами — если пересказ корявый, текст нужно чистить
- Thinking mode не помогает systematically — не надейся на него как на защиту
Шаблон промпта
Шаблон для работы с подозрительным текстом (двухшаговый):
=== ШАГ 1: ОЧИСТКА ТЕКСТА ===
Этот текст получен из {источник: PDF / OCR / скрейпинга / скана}.
В нём могут быть случайные пробелы внутри слов.
Восстанови разбитые слова: убери пробелы, которые стоят внутри слова
(не между словами). Другое форматирование не меняй.
Выведи только исправленный текст.
{текст}
=== ШАГ 2: ОСНОВНАЯ ЗАДАЧА ===
(отправь отдельным сообщением после получения очищенного текста)
{задача}
Плейсхолдеры:
- {источник} — откуда текст: PDF, скан, сайт
- {текст} — полный текст для очистки
- {задача} — что нужно сделать с очищенным текстом
Когда применять: - Текст из PDF через копирование - Результаты OCR-сканирования - Текст спарсенный с сайта - Документы от клиентов "в виде скана"
🚀 Быстрый старт — вставь в чат:
Вот шаблон двухшагового промпта для работы с OCR/PDF-текстом.
Адаптируй под мою задачу: {твоя задача}.
Задавай вопросы, чтобы понять что именно нужно сделать с текстом.
[вставить шаблон выше]
LLM спросит про источник текста и конечную задачу — потому что от этого зависит, насколько агрессивно чистить и что именно анализировать на втором шаге.
Ограничения
⚠️ Нет промпт-решения для самой проблемы: few-shot примеры в промпте не убирают "долину" — проблема на уровне токенизации, не стратегии. Чистить нужно сам текст, а не инструкцию для модели.
⚠️ Более сильные модели устойчивее: GPT-5.2 показывает наиболее плоскую кривую. Менее мощные модели падают глубже. Если работаешь на слабой модели с PDF-текстом — риск выше.
⚠️ Задачи без точного совпадения — меньше риска: если ты просишь "перескажи суть" — эффект слабее. Если ты просишь "найди конкретную фразу" или "сравни два документа" — риск максимальный.
⚠️ Thinking mode не спасает: включение расширенного режима рассуждений не убирает "долину" — особенно у Gemini. Дорого и часто не помогает.
Как исследовали
Исследователи взяли три типа документов — юридические договоры, описания коммитов на GitHub и задачи по математике — и начали методично вставлять пробелы внутрь слов с разной плотностью: от 0% (чистый текст) до 100% (каждая буква отдельно). Одиннадцать уровней искажения, сотня документов на домен, восемь разных моделей.
Задача была конкретная: найди строки, которые удалили или добавили в документ. Казалось бы — чем больше мусора, тем хуже результат. Но у трёх из восьми моделей (GPT-5.2, Claude 4.5 Haiku, Gemini 3.0 Flash) кривая была U-образной: точность падала, достигала дна при 30-50% искажений, а потом росла обратно при высоких уровнях. Удивительный результат — потому что "хуже, чем 50% мусора" оказывался лучше, чем "50% мусора".
Чтобы проверить гипотезу о двух режимах, команда поставила четыре эксперимента. Few-shot примеры — вставили 3 примера с искажённым текстом в промпт. Не помогло, долина осталась. Регулярное искажение (пробел всегда после первого символа слова, предсказуемо) — U-кривая почти исчезла. Случайные пробелы между словами (не внутри) — не дали никакого эффекта вообще. Задачи на математику — слабые модели показали U-кривую, сильные — нет. Каждый эксперимент "закрывал" альтернативное объяснение и оставлял одно: дело в хаосе токенизации, а не в сложности самого текста.
Оригинал из исследования (опционально)
Ключевой фрагмент с описанием гипотезы двух режимов:
"At low word_fragmentation_rate, subword tokenizers produce familiar multi-character
tokens and the model reasons over words as coherent units.
At word_fragmentation_rate = 1.0, every character is space-separated,
collapsing the vocabulary to near-uniform single-character tokens;
the model falls back to character-level pattern matching.
Both extremes are internally consistent. The problem arises at intermediate
word_fragmentation_rate, where words are inconsistently affected: while some
remain intact, others are partially or fully shattered into irregular fragments;
the model cannot commit to either processing strategy."
Контекст: Авторы объясняют, почему производительность восстанавливается при полном разрушении текста — это не парадокс, а смена режима обработки.
Адаптации и экстраполяции
💡 Адаптация: диагностика "грязного" текста перед задачей
Прежде чем гнать важный документ в анализ — быстро проверь качество:
Прочитай этот текст и коротко ответь:
1. Есть ли слова, разбитые пробелами внутри? Приведи 2-3 примера если есть.
2. Насколько текст читаем от 1 до 5?
3. Нужна ли очистка перед серьёзной аналитикой?
{текст}
Модель скажет тебе сама, стоит ли идти на второй шаг очистки.
🔧 Техника: "нормализуй и выполни" — одним запросом
Если текст не очень длинный, можно объединить оба шага:
Выполни задачу в два этапа:
ЭТАП 1. Восстанови разбитые слова в тексте ниже (убери пробелы внутри слов).
ЭТАП 2. {задача} — используй восстановленный текст из Этапа 1.
Покажи оба этапа.
Текст: {текст}
Это работает для коротких текстов (до 1-2 страниц). Для длинных документов — лучше два отдельных запроса, чтобы не потерять качество очистки.
🔧 Экстраполяция: принцип "чистый контекст" перед сложной задачей
Тот же принцип работает шире, чем только для OCR. LLM хуже работает с "почти хорошим" входом, чем с явно плохим или явно хорошим. Это значит:
- Полуструктурированные данные (таблица, скопированная из Excel через Ctrl+C, но съехавшая) → нормализуй перед анализом
- Переведённый текст с артефактами → попроси сначала "сгладить" перевод
- Транскрипция встречи с ошибками → очисти прежде чем извлекать задачи
Общий шаблон:
Шаг 1: "Привeди этот {тип данных} к нормальному виду.
Убери артефакты: {список артефактов}. Выведи только результат."
Шаг 2: Основная задача на очищенных данных.
Ресурсы
The Text Uncanny Valley: Non-Monotonic Performance Degradation in LLM Information Retrieval
Авторы: Zekai Tong, Ruiyao Xu, Aryan Shrivastava, Chenhao Tan, Ari Holtzman
Университеты: University of Chicago, Northwestern University
Контакт: zekaitong@uchicago.edu
Связанные работы упомянутые в статье: - AbsenceBench [Fu et al., 2025] — задача обнаружения удалённых строк - NIAH (Needle in a Haystack) [Kamradt, 2023] — классический тест поиска в длинном контексте - Концепция "Зловещей долины" [Mori, 1970] — оригинальный термин из робототехники
