Это исходный отчёт фазы как есть — со всеми таблицами и методикой. Живая версия: 📚 Поиск по документам (RAG).
Фаза 8: поиск по документам (эмбеддинги, реранкинг, RAG)
Прогон: 21–22 октября 2026
Хост: UGREEN DXP4800 Pro, i3-1315U, 32 GB, iGPU Intel RPL-U (Xe-LP, 64 EU)
Что меряли: насколько хорошо модели эмбеддингов находят нужный русский фрагмент, сколько времени занимает индексация на NAS и насколько хорошо LLM отвечает на вопросы по найденному.
Коротко
- Лучший поиск по-русски — bge-m3. На MIRACL nDCG@10 84.3, нужный фрагмент в топ-10 в 93% случаев. Это 200 вопросов по 31.7 тыс. фрагментов Википедии. Запрос обрабатывается за 83 мс.
- Но индексация медленная: 5.9 фрагментов/с на iGPU, корпус 31.7 тыс. занял 89 мин.
- EmbeddingGemma-300M чуть слабее (80.0), зато вдвое быстрее: 49 мин, 52 мс на запрос.
- Новая EmbeddingGemma-2 между ними: 81.6, 73 мин.
- Qwen3-Embedding 0.6B и 4B на этом iGPU непрактичны. На одних и тех же абзацах XQuAD они в 2 и 8 раз медленнее bge-m3 (1.7 и 0.4 абзаца/с против 3.3), MIRACL за 3 ч не успели. На маленьком XQuAD 4B лучший (97.1), но 550 мс на запрос.
- RAG работает. Qwen3.5-4B по трём абзацам, найденным bge-m3, отвечает верно в 83% случаев. С заведомо правильным абзацем — в 87%, без контекста — в 4%. Поиск почти не теряет: нужный абзац попадает в топ-3 в 99.3% случаев. Ответ занимает ~6 с.
- Строгие метрики SQuAD для русского занижают результат. EM 46% и F1 69%, потому что «308 очков» ≠ «308», а «Мэннинг» ≠ «Мэннинга». В таблице есть мягкая оценка, учитывающая окончания.
- Реранкер bge-reranker-v2-m3 поднимает поиск, но дорого. Пересортировка топ-20 от bge-m3 даёт на MIRACL nDCG@10 88.1 вместо 84.3 и MRR 90.7 вместо 88.4, но стоит 8.6 с на вопрос (20 пар на iGPU). Qwen3-Reranker-0.6B выигрыша не дал (84.0) при 13.1 с на вопрос. Первый прогон на XQuAD (1190 вопросов × 30 пар) не уложился в 2 ч, поэтому реранкеры мерили отдельно, на MIRACL.
Как мерили
- Данные:
- MIRACL, русская часть в версии MTEB с трудными отрицательными примерами (CC-BY-SA-4.0): 200 случайных вопросов из 1000; корпус — все фрагменты, размеченные для этих вопросов (572 нужных и 1518 размеченных как нерелевантные), плюс 30 000 случайных из 219 тыс.;
- XQuAD ru (CC-BY-SA-4.0): 1190 вопросов по 240 абзацам, ответ — фрагмент текста.
- Модели эмбеддингов: bge-m3 (ggml-org Q8_0), EmbeddingGemma-300M и EmbeddingGemma-2 (ggml-org Q8_0), Qwen3-Embedding 0.6B (Q8_0) и 4B (Q4_K_M, GGUF от Qwen). Префиксы запросов и документов взяты из карточек моделей.
- Сервер: llama.cpp
server-vulkanbuild 11718,--embeddings,-np 8 -b 2048 -ub 2048, по 32 фрагмента в запросе. - Реранкеры: bge-reranker-v2-m3 (FP16), Qwen3-Reranker-0.6B (Q8_0),
--reranking. - RAG: Qwen3.5-4B (
--reasoning off) получает вопрос и топ-3 абзаца, отвечает «коротко, словами из текста». 300 вопросов XQuAD. - Воспроизведение:
- на NAS:
run_rag.sh emb|rerank|answer,chain.sh; - данные готовит
prepare_rag.py, оценка —rag_eval.py; - сырые результаты лежат в
raw/, таблицы генерируетpython3 make_report.py.
- на NAS:
Поиск: эмбеддинги
MIRACL ru — 200 вопросов, корпус 31 737 фрагментов Википедии (все размеченные для этих вопросов + 30 000 случайных); XQuAD ru — 1190 вопросов по 240 абзацам. Косинусная близость, полный перебор. «Индекс» — время на корпус MIRACL (фрагменты обрезаны до 2000 символов, медиана ~360), «запрос» — эмбеддинг одного вопроса.
| Модель | Размер | MIRACL nDCG@10 | MIRACL recall@10 / @100 | XQuAD nDCG@10 | XQuAD recall@10 | Фрагментов/с | Индекс MIRACL, мин | Запрос, мс |
|---|---|---|---|---|---|---|---|---|
| bge-m3 | 568M, Q8_0 | 84.3 | 92.7 / 99.6 | 96.0 | 99.6 | 5.9 | 89 | 83 |
| EmbeddingGemma-300M | 300M, Q8_0 | 80.0 | 92.0 / 100.0 | 96.3 | 99.5 | 10.7 | 49 | 52 |
| EmbeddingGemma-2 | Q8_0, сентябрь 2026 | 81.6 | 93.7 / 99.9 | 95.5 | 99.3 | 7.3 | 73 | 66 |
| Qwen3-Embedding-0.6B | Q8_0 | — | — / — | 93.6 | 98.4 | 1.7 | не успел за 3 ч | 123 |
| Qwen3-Embedding-4B | Q4_K_M | — | — / — | 97.1 | 99.9 | 0.4 | не успел за 3 ч | 550 |
Поиск: реранкинг топ-20 bge-m3 (MIRACL)
| Вариант | nDCG@10 | recall@10 | MRR@10 | На вопрос, мс |
|---|---|---|---|---|
| только bge-m3 | 84.3 | 92.7 | 88.4 | 83 |
| bge-m3 + bge-reranker-v2-m3 | 88.1 | 94.5 | 90.7 | 8599 |
| bge-m3 + Qwen3-Reranker-0.6B | 84.0 | 94.5 | 84.8 | 13109 |
Ответы по найденному (RAG), XQuAD ru, Qwen3.5-4B
300 вопросов. EM/F1 — стандартные метрики SQuAD (строгие к падежам и единицам: «308 очков» ≠ «308»); «верно» — ответ совпадает с эталоном с точностью до окончаний и единиц; «отказ» — модель ответила, что в тексте нет информации. «Найдено» — доля вопросов, где нужный абзац попал в топ-3.
| Контекст | EM | F1 | Верно, % | Отказов | Найдено, % | Ответ, с |
|---|---|---|---|---|---|---|
| без контекста | 2.3 | 8.0 | 4.0 | 1 | 0 | 1.46 |
| правильный абзац | 50.0 | 72.3 | 86.7 | 2 | 100 | 3.19 |
| топ-3 от bge-m3 | 46.0 | 69.1 | 83.3 | 3 | 99.3 | 6.05 |
Выводы и рекомендации
- Для поиска по своим документам на NAS — bge-m3. Если индексировать нужно быстро, EmbeddingGemma-300M: качество на 4 пункта ниже, скорость вдвое выше. Индекс строится один раз, дальше дописываются только новые документы, а запрос в любом случае мгновенный.
- Сколько это на практике. 10 тысяч страниц — это ~50 тысяч фрагментов, индексация bge-m3 займёт ~2.5 ч на iGPU (EmbeddingGemma-300M — ~1.3 ч). Для домашнего архива это терпимо: один раз и ночью.
- Отвечать по найденному может та же Qwen3.5-4B, что и везде: ~6 с на ответ, 83% верных на XQuAD. Слабое место — отказы «в тексте нет информации», когда ответ нужно чуть вывести: например, возраст из даты рождения.
- Реранкер — только когда точность важнее скорости. bge-reranker-v2-m3 чаще ставит нужный фрагмент первым (+3.8 nDCG@10), но добавляет ~8.6 с к каждому вопросу, а ответ LLM и так занимает ~6 с. Для RAG по топ-3 выигрыш небольшой: нужный абзац и без реранкера попадает в топ-3 в 99% случаев на XQuAD. Можно сократить цену, пересортировывая топ-10 вместо топ-20.
- Для фреймворка. Эмбеддинги на llama.cpp Vulkan на этом iGPU медленные, ~600 токенов/с даже для модели на 0.6B. Стоит сравнить с OVMS (OpenVINO, int8) — в фазе 2 OpenVINO на этом же iGPU оказался в 3.3 раза быстрее. Здесь сравнение не проводилось.
Ограничения
- Корпус MIRACL урезан до 31.7 тыс. фрагментов. На полном корпусе (219 тыс.) nDCG ниже, но порядок моделей, скорее всего, тот же.
- XQuAD почти не различает модели: все 93–97 nDCG, корпус всего 240 абзацев.
- OpenVINO не сравнивался, см. выше. Реранкеры мерили только на MIRACL (200 вопросов, топ-20 от bge-m3), разница меньше ~3 пунктов nDCG в пределах шума.