localaiforum
Войти
Руководство › Работа с моделями

Дообучение с LoRA и QLoRA

Дообучение настраивает поведение, а не знания. Это правильный инструмент, когда модель знает материал, но танцует не тот танец: неверный формат вывода, неверный тон, неверный диалект домена, неверная калибровка отказов. Это неправильный инструмент для «знает мои документы» — это ретривал: RAG.

Тюнить или нет

Цель Возьмите
Отвечать на вопросы по моим документам RAG
Всегда выдавать мой точный формат JSON/XML LoRA — или грамматически-ограниченное декодирование
Писать в едином фирменном стиле LoRA
Перестать отказывать легитимным запросам домена LoRA, с осторожными данными
Свободно говорить на диалекте моего домена LoRA, затем RAG сверху
Лучше рассуждать Модель побольше или получше — тюнинг не добавит IQ

Если промпт или схема могут это сделать, предпочитайте промпт или схему. Тюньте, когда ловите себя на вставке одних и тех же 300 токенов инструкций в каждый вызов.

LoRA в одном абзаце

Заморозьте каждый базовый вес. Для каждой целевой матрицы весов добавьте две маленькие обучаемые матрицы — A (r×d) и B (d×r) — и обучайте только их. Обновление низкоранговое:

W' = W + (alpha / r) · B·A      # A это r×d, B это d×r, ранг r << d

Конкретно: матрица d = 4096 при ранге r = 16 требует 2 × 4096 × 16 = 131k параметров адаптера вместо 4096² ≈ 16.8M плотных — 0.8% той матрицы. По модели 7–8B адаптеры в сумме дают ~40–80M параметров: 0.5–1% базы, несколько сотен MB. Этой ёмкости хватает, чтобы жёстко сдвинуть стиль и формат, потому что эти поведения живут в сильно низкоранговых направлениях.

QLoRA: одна потребительская карта

QLoRA держит замороженную базу квантованной в 4 бита (NF4) во время обучения и гоняет адаптеры в 16-битных числах. Рабочие числа на текущих стеках: модель 7–8B QLoRA-обучается на одной GPU 24GB; 3B обучается комфортно в 8GB. Градиентный чекпойнтинг и пейджиновые оптимизаторы берёт на себя инструментарий — что поставляете вы, так это математику бюджета: математика VRAM.

Данные бьют всё

500–5,000 качественных пар бьют 100k наскобленных, всегда. Правила, которые важны:

  • Один консистентный формат. Используйте точно тот чат-шаблон, с которым будете обслуживать, — несовпадение шаблонов train/serve перечёркивает весь прогон.
  • Качество важнее объёма. Каждая пара должна быть выводом, который вы приняли бы от модели. Дедуплицируйте; выбрасывайте ленивые примеры.
  • Покрытие. Включите случаи, где модель должна отказать или обработать особо — иначе она переносит новое поведение на всё подряд.
  • Проверки на контаминацию. Убедитесь, что eval-вопросы не встречаются в обучающих данных — иначе вы оцениваете зазубривание.
  • Отложенный eval-набор. 50–100 примеров, на которых никогда не обучаетесь, с оценкой до и после.

Как выглядит пара (формат messages, который потребляет большинство инструментов):

{"messages": [{"role": "system", "content": "You are a 1998-era equipment manual assistant."},
              {"role": "user", "content": "How do I reset the service counter?"},
              {"role": "assistant", "content": "Press MENU and hold for 3 seconds..."}]}

Инструменты

Инструмент Почему выбрать
Unsloth самые быстрые тренеры для одной GPU, бесплатные комьюнити-ноутбуки — лёгкий старт
Axolotl конфигурационно-управляемый, широкая поддержка форматов датасетов, воспроизводимые рецепты
LLaMA-Factory GUI плюс CLI, сильная мультиязычная экосистема датасетов

На момент написания все три активно поддерживаются: unsloth, axolotl, llama-factory.

Гиперпараметры, которые реально важны

В порядке влияния:

  • Learning rate — 1e-4 до 2e-4 для QLoRA — здравая полоса; слишком высокий — обычная причина каши.
  • Эпохи — 1–3. Больше — откуда берётся подхалим.
  • Ранг / alpha — r 8–32 с alpha 16–32 покрывает большинство правок поведения; ранг побольше для сдвигов с тяжёлым доменом.
  • Длина контекста — под ваш самый длинный реальный пример, а не дефолт тренера.
  • Размер батча — 1–8 нормально для QLoRA на одной карте; это ручка пропускной способности, а не качества.

Если прогон разочаровывает, чините сначала данные, потом learning rate, ранг — последним.

Время и стоимость

QLoRA на 2,000 пар, 3 эпохи, модель 7–8B: ждите 1–3 часа на одной карте класса RTX 3090/4090. Это электричество, а не счета за API, и итерация — максимум одна ночь. Поэтому локальное дообучение — хобби, а не процесс закупки.

Закладывайтесь на итерацию: первый прогон учит вас проблемам данных, второй — тот, что остаётся.

Оцените перед релизом

Прогоните фиксированный набор из 30–50 промптов — включая отложенный — до и после; сравните выводы бок о бок. Затем регресс-проверьте общий чат: классический провал — доменно-затюненная модель, отвечающая на всё в формате баг-репортов. Если общее качество упало, меньше эпох, ниже learning rate или подмешайте 10–30% общих инструктивных данных в прогон.

Кривые лосса — чтобы заметить расходимость, а не чтобы оценивать: обучающий лосс должен упасть и выйти на плато. Арбитр — eval-набор.

Экспорт и обслуживание

Два пути из обученного адаптера:

  • Вмержить LoRA в базу в fp16, затем конвертировать в GGUF для llama.cpp — дружественный форуму артефакт: один файл, любой движок: форматы моделей, квантизация.
  • Держать адаптер отдельно для transformers/vLLM, которые грузят базу + адаптер в рантайме — дешевле итерировать, движко-специфично.

Режимы отказа

  • Переобучение / «подхалим» — эхо вашего промпта, согласие со всем; обучающий лосс низок, eval хуже. Фикс: меньше эпох, ниже LR, более разнообразные данные.
  • Катастрофическое забывание — доменный навык вверх, общая способность вниз. Фикс: подмешать общие данные; ниже LR.
  • Дрейф шаблона — обучена с одним чат-шаблоном, обслуживается с другим; симптомы — классика из диагностики.

DPO после SFT

Когда формат верен, но предпочтения не те — слишком многословно, не тот тон, сверх-отказчивость, — маленький DPO-прогон на парах предпочтений (chosen против rejected) правит поведение без ещё одного SFT-прохода. Дёшево, стабильно и стандартная вторая стадия рецепта SFT-затем-DPO.

Связанные разделы: rag · форматы моделей · квантизация · математика VRAM