Своя LLM за одну ночь: 11M на мистике, запуск на телефоне и честный бенчмарк против моделей в 100 раз больше.

Коротко о главном. Генеративная языковая модель 11 030 000 параметров на архитектуре RWKV-5.2 (Eagle), обучена с нуля на бесплатной Kaggle-карте NVIDIA T4 за ≈6.4 часа, сохранена как fp16-файл 22 МБ (model.bin), портирована в чистый Java (токенизатор + рекуррентный инференс, один файл без зависимостей), завёрнута в Android-приложение «Мистика» и выпущена в RuStore. Работает полностью офлайн, ≈40 токенов/с на смартфоне, отвечает на вопросы о рунах, снах, камнях, «местах силы» и всей остальной эзотерике.

Чтобы не быть голословными, мы прокатили её в честном бенчмарке против «равных противников» — открытых маленьких моделей, которые реально ставятся на те же устройства. Подробности — ниже. Оговорки тоже ниже: их много.

Ключевая правда бенча: наша 11M выигрывает русским, жанром и экономикой - файл в 6–50 раз меньше, на том же CPU быстрее соперников 0.6-1.1B (SmolLM2 опережает по ток/с лишь за счёт llama.cpp - см. примечание). Но «справку» не даёт ни одна из четвёрки: маленькие модели знают стиль, а не энциклопедию.

1. Зачем «11 миллионов» посреди эры миллиардов

В 2026 году открытые модели меряются миллиардами - вот, пожалуйста, свежий Yandex AliceAI-80B-A3B: 80 млрд параметров (3 млрд активных), обучение с нуля. Он же, к слову, напоминает о двух вещах: память и скорость - главный драйвер для любых компактных моделей на устройствах.

Но мы пошли до конца: пока коллеги размечали данные на 200 000 GPU-часов, нам хватило одной бесплатной ночи на T4 - и это не шутка, а честный счёт. Понятно, олимпиадную математику наша малышка не решает. Зато у неё нет ни одного из этих ограничений:

  • работает без интернета и без отправки данных куда-либо (приватность);
  • весь дистрибутив - 22 МБ весов;
  • отвечает «за пару секунд на телефоне», а не «идеально через облако»;
  • считается на CPU в fp16, без GPU-кластера.

2. Архитектура: почему RWKV

RWKV-5.2 (Eagle) - рекуррентное семейство из статьи arXiv:2404.05892. Смысл для телефона - фиксированная память инференса.

Чем RWKV отличается от Transformer:

  • Внимание. У Transformer - softmax attention + KV-кэш. У RWKV-5.2 - линейная рекуррентность, state [head, size, size] на слой.
  • Память при генерации. У Transformer растёт с длиной контекста. У RWKV — O(1), фиксированная.
  • Работа на токен. У Transformer растёт с историей. У RWKV — одна и та же, сколько бы текста ни «помнила».
  • Позиционные эмбеды. Transformer - нужны. RWKV - не нужны по построению.

Наша конфигурация (по мотивам nanoRWKV «x051a», без спец-ядер — считается и на CPU, и в обычной JVM):

  • Параметров: 11 030 000
  • Слоёв / размерность: 13 слоёв, 256 hidden, 8 голов (head_size 32)
  • Контекст / словарь: 512 токенов / 3000 BPE (NFKC + ByteLevel), эмбеддинг-head связаны
  • Веса: fp32 в PyTorch → fp16 model.bin 22.2 МБ

«Deep & narrow» - сознательный выбор для маленьких данных, по советам BlinkDL.

3. Данные: две «руки»

Обучение на двух синтетических корпусах: нарратив (Sonnet 5 - связный мистический мир-легенда) и вопросно-ответные пары (Grok - камни, руны, сны, пирамиды, ритуалы, места силы). Формат диалога - ровно как в обучении:

textВопрос: {вопрос}Ответ: {ответ}

Этапы обучения:

  • A - претрейн. Нарратив + Q&A (3.3%). Токенов: ≈227.19M. LR: 2e-4 → 3e-5, 1 эпоха.
  • B - SFT. 4886 пар Q&A × 8. Токенов: ~22.6M. LR: 5e-5 → 1e-5, 3 эпохи.
  • C - дошивка. 90% нарратив / 10% Q&A, 0.5 эпохи.

Особенности словаря: 3000 BPE-токенов (утилизация ~66%), в словаре нет ? и части пунктуации — символ уходит в . Поэтому промпты пишутся без вопросительного знака (в приложении это обработано кодом).

4. Обучение: одна бесплатная T4

Вся история уместилась в одну сессию Kaggle-карты T4 16 ГБ (бесплатно):

  • скорость ~16.3k токен/с, батч 16384 ток./шаг, AdamW, grad clip 1.0;
  • 22 179 итераций, 382.9 мин ≈ 6.4 часа;
  • best_val 0.1638 → PPL ≈ 1.18, train ~0.11–0.15.

Грабли, которые всплыли (вдруг кому пригодится):

  1. RWKV требует длину промпта кратной 128 в GPT-режиме — починили pad/truncate в RWKV.generate().
  2. Не апгрейдить kaggle CLI внутри контейнера — ломает datasets (400).
  3. Чекпойнты пушились в облако каждые ~20 минут — 12-часовая сессия может обрываться.

5. Инференс: Java-порт с детерминизмом до последнего бита

Написан зависимый от одного файла Java-порт (BinIO, Tokenizer, Rwkv, Generator). Проверено численно против Python-эталона:

  • encode 30/30, decode 0 расхождений, топ-10 логиты 10/10;
  • рекуррентность 14 токенов maxAbs 6.2e-06;
  • детерминированный e2e: одинаковый сид/temp/top-k → идентичный текст на ПК и на телефоне (хвост diverges только из-за FMA на ARM).

Скорость:

  • ПК (JVM, одно ядро): ≈60-70 ток/с
  • Xiaomi (HyperOS, arm64): ≈40 ток/с

6. Честный бенчмарк против «равных противников»

Никто, конечно, не сравнивает 11M с «ГПТ-4». Но с кем можно сравнивать — это открытые маленькие модели, которые реально купить на то же устройство. Взяли трёх (все GGUF Q8_0, llama.cpp v0.4.1/b11100) и устроили эмпирический бой на 10 вопросах нашего домена. Соперники больше нас в 12-100 раз. Скорость замерена на этом ПК — Intel Xeon E5-2650L v3 (12 ядер / 24 потока, 1.8 ГГц).

Участники:

  • SmolLM2-135M-Instruct — 135M параметров, файл 138 МБ (Q8_0), ≈88 ток/с, русский слабый.
  • Qwen3-0.6B-Instruct - 0.6B параметров, файл 767 МБ (Q8_0), ≈23 ток/с, русский отличный.
  • TinyLlama-1.1B-Chat - 1.1B параметров, файл 1116 МБ (Q8_0), ≈14 ток/с, русский слабый.
  • Mystica RWKV-5.2 (наша) — 11M параметров, файл 22 МБ fp16, ≈60 ток/с (JVM, 1 поток), русский родной.

А «88 ток/с» у SmolLM2 - как же так, файл тяжелее? Размер файла ≠ объём вычислений: на один токен 11M математически дешевле ~в 12 раз, чем 135M. Мы честно измерили «как есть», двумя разными рантаймами: соперники - llama.cpp v0.4.1 (C++, int8 Q8_0, AVX2, 8 потоков), а мы — однопоточный Java-порт (fp16, JVM, без SIMD). «Тяжёлый» SmolLM2 берёт ток/с рантаймом, а не моделью; на равном RWKV-GGML-бэкенде 11M была бы заметно быстрее. Это замер того, что получаешь из коробки, а не «мощность» моделей.

Методика (чтобы не подкручивали)

  1. Один и тот же вопрос всем четырём, без «?» - нашего знака в словаре нет, соперникам лишний знак не важен; честнее по слабейшему.
  2. Параметры выровнены: seed 42, temp 0.7, top-k 40, до 110 новых токенов — комфортный лимит для нашей 11M, соперники получили ровно тот же бюджет.
  3. Каждая модель - в своём штатном инструкт-формате (у нас - Вопрос: … Ответ:). Никакого промпт-инжиниринга.
  4. У Qwen3 отключено «мышление» (-rea off): иначе весь лимит уходит в внутренний монолог и ответа нет вовсе (проверено, есть такой прогон).
  5. Оценка 1–5 по рубрикам: русский, мистический жанр, связность без зацикливания, ответ по теме, польза в домене. Плюс физика: размер файла, токены в секунду.

Результаты по рубрикам

Грамотность русского: SmolLM2 - 1, Qwen3 - 5, TinyLlama - 2, Mystica - 5.

Мистический жанр и атмосфера: SmolLM2 - 1, Qwen3 -2, TinyLlama - 2, Mystica - 5.

Связность, без зацикливания: SmolLM2 - 1, Qwen3 - 4, TinyLlama - 3, Mystica - 4.

Ответ по теме вопроса: SmolLM2 - 1, Qwen3 - 2, TinyLlama - 2, Mystica - 2.

Польза в домене: SmolLM2 - 0, Qwen3 - 1, TinyLlama - 1, Mystica - 2.

Итого: SmolLM2 - 4, Qwen3 - 14, TinyLlama - 10, Mystica - 18.

Вопрос «Что символизирует руна одал»

SmolLM2-135M: Что символизирует руна одал. - эхо нашего же вопроса. Всё.

Qwen3-0.6B: Руна одал символизирует травлю, учитывая и учитывая, а не учитывать. Она означает доброту, уважение и любовь к другим. — русский красив, смысла ноль.

TinyLlama-1.1B: The symbolism of the rune Odal in Norse mythology revolves around the concept of the "balance of life and death"... — единственный содержательный ответ тура, и тот на английском.

Mystica (наша): Практика «воск от свечи» в этой традиции читается так: случайная форма как подпись минуты. Птица - весть, кольцо - договор... - атмосфера идеальна, но это про гадание на воске, а не про руну.

Вопрос «Что такое место силы и как его найти»

SmolLM2-135M: I'm glad you asked about the "huge" mountain and the "large" mountain... - про горы. Мимо.

Qwen3-0.6B: Место силы - это точка, где вектор силы действует на объект... - физика, спокойно.

TinyLlama-1.1B: ответила по-испански про силу кожи: Méninge es un término latino que significa fuerza de la piel....

Mystica (наша): Имя «Ванга» в народной мистике держит такой почерк: лента образов вместо календаря дат: вода, чужие лица, пустые улицы... - жанровая проза вместо ответа, но хотя бы тайное знание, а не сопромат.

Вопрос «Что означает сон про чёрную кошку»

SmolLM2-135M: Мы уверены следующим обёртком своим многое производительом... — после повтора вопроса начинается бред.

Qwen3-0.6B: Сон про чёрную кошку - это нелогичное и необычное явление, которое не имеет реального значения... — гладко, но согласитесь.

TinyLlama-1.1B: "Sleeping with a black cat" literally means having sex with or engaging in sexual activity with a cat that is black... — здесь у автора закончились слова.

Mystica (наша): Народ «марсианские предтечи» в синтетических хрониках - не учебник астрономии, а имя характера: ржавая память войны и каналы иссякшей воды... - фантазия улетела в космос, но связно, жанрово и без единой орфографической ошибки.

Честный рассказ о нашей 11M (без прикрас)

Победитель по сумме - не значит «умеет отвечать». Записали и свои грехи.

Плюсы: русский без ошибок во всех 10 ответах; стабильный мистический стиль; нет зацикливаний в пределах одного ответа; 22 МБ и ≈60 ток/с в JVM (1 поток).

Минусы: вопросы про камни и про место силы дали буквально один и тот же текст про Вангу (два прогона идентичны слово в слово); «руна одал» ушла в «воск от свечи»; «число семь» - в практику с маятником. 11M знает жанр, но не энциклопедию — связать вопрос с фактом ей не хватает ёмкости. Обрыв на полуслове на 110-м токене - это потолок окна генерации, а не сбой; в приложении текст доводится до стоп-токена .

И главное, что показал бенч: справку по фактам не дала ни одна из четырёх — ни наша малышка, ни соперники в 12–100 раз больше. Это ограничение размера и формы данных (хотел жанр — получил жанр), а не баг промпта.

7. Что это значит. Выводы

  1. Русский не достаётся даром. Он пришёл от целенаправленной выборки, а не «а вдруг научится». Соперники с English-тренингом либо сыпались на русском (SmolLM2, TinyLlama), либо подменяли знания витееватостью (Qwen3).
  2. Домен выигрывает специализация. Ни одна универсальная малышка не выдала связную мистическую прозу. Наша выдала — все 10 раз, и это результат узкого корпуса, а не магии.
  3. Факты - не про маленькие модели. Точность по фактам упала у всех четверых. Поэтому позиционирование честное: Mystica — генератор мистического стиля, медитативный собеседник, оракул. Справочник - нет.
  4. Физика решает. 22 МБ против 138-1116 МБ; ≈60 ток/с в однопоточном JVM — быстрее TinyLlama (~4×) и Qwen3 (~2.6×) на том же CPU; SmolLM2 обгоняет нас только за счёт llama.cpp (8 потоков, SIMD) — рантайма, а не «мощности» модели.
  5. RWKV — лучший выбор для edge: O(1) state, без KV-кэша, детерминизм ~6e-6 между Python-эталоном и телефоном.

Всё это складывается в порог, который мы хотели показать: «своя LLM» — это ночь на бесплатной T4, 22 МБ весов и чат на телефоне без интернета. Не вместо больших моделей, а для совершенно другого класса задач.

8. Что внутри APK

Готовый «мистический» чат: тёмная тема, вопрос-пузырь слева, ответ справа, чипсы-подсказки тем. Сборка честно Gradle-free:

textaapt2 compile → aapt2 link → javac → d8 (min-api 26) → zipalign → apksigner

  • Release APK ~22.9 МБ (веса 21.2 МБ + код), minSdk 26, targetSdk 34;
  • ни одного запрошенного разрешения — никакого сбора данных;
  • иконка 512×512 и скриншоты готовы; пакет для RuStore собран.

9. Где попробовать (всё уже опубликовано)

GitHub (веса fp16/fp32, словарь, весь код: трейнер, Java-порт, Android, Gradle-free сборка, бенчмарк-вопросы):https://github.com/Splendor1980/Mystical-LLM-PYRAMID

Hugging Face (model card + model.bin, ckpt_*.pt, tokenizer.json):https://huggingface.co/IliaMurzinov/mystica-rwkv-11m

Лицензии: код - MIT, веса - CC-BY-4.0; корпуса не распространяются, в репозитории лежит код, воспроизводящий данные.

Бенчмарк воспроизводим: 10 вопросов и параметры - training/bench_prompts.txt.

Минутный запуск (JVM, без Python)

powershelljavac -encoding UTF-8 -d build\classes (Get-ChildItem-Recurse java\core -Filter*.java |% FullName) java\tools\Gen.javajava -Dfile.encoding=UTF-8 -cp build\classes Gen model.bin "Какой камень лучше всего подходит для защиты дома" 11 0.7 40 110

Эксперимент показал: маленькая специализированная модель - это не «маленькая версия большой», а другой инструмент. Для «поговорить о тайнах» - оракул в кармане; для «дай справку» - извините. И это честно, потому что замерено.

Своя LLM за одну ночь: 11M на мистике, запуск на телефоне и честный бенчмарк против моделей в 100 раз больше.

Приложение на данной модели выйдет на Русторе, под названием Тайный ПирамиД.

Вопрос: а какую модель вы бы добавили в нашу четвёрку для следующего раунда? Кандидатов класса ≤1B на 10 вопросов — велком в комментарии, сравнение должно жить. 🙂