Муки выбора: как я подбирал локальную модель для кодинга на 16 ГБ VRAM и трижды менял фаворита
Изначально я подобрал модель, которая великолепно генерировала исходный код. Интегрировав её в OpenCode, я быстро обнаружил фатальный недостаток: создавать файлы на жестком диске она оказалась неспособна. Следующая кандидатка уверенно оперировала файлами, но сокрушительно проваливалась при малейшей попытке использовать русский язык.
В конечном итоге пальма первенства досталась решению, изначально отложенному «на растерзание»: громоздкой модели, балансирующей на грани жесткого квантования и казавшейся сплошным компромиссом.
Ниже подробно описан процесс поиска идеального помощника для WordPress и фронтенд-задач на графическом ускорителе с 16 ГБ памяти. В программе — замеры скорости, нюансы квантования и неожиданно суровый экзамен по русскому языку.
Для каких задач я её искал
Моя стихия — разработка под WordPress. Типичный стек включает PHP, HTML, CSS, JavaScript, интеграцию готовой верстки и проектирование блоков Gutenberg.
От локальной языковой модели требовался вполне конкретный функционал: анализировать существующий кодовая база, вносить точечные правки, генерировать файлы и неукоснительно соблюдать регламент проекта. В том числе корректно формулировать на русском языке наименования полей, которые впоследствии отображаются в административной панели.
Поскольку взаимодействие осуществлялось через OpenCode, банального умения писать код было недостаточно. Требовались полноценный вызов инструментов (function calling), адекватный русский язык и высокая скорость ответа, не заставляющая забывать суть исходного запроса. И всё это — в строгих рамках 16 ГБ VRAM с учетом контекста.
Контекстное окно при этом неизбежно разделяют системные промпты, исходный код, история диалогов и результаты выполнения утилит. Сам факт загрузки весов в видеопамять вовсе не гарантирует наличие свободного пространства для продуктивных вычислений.
Эффективность оценивалась исключительно по рабочим кейсам, а производительность и потребление памяти фиксировались на следующей рабочей станции:
|
Компонент |
Моя конфигурация |
|---|---|
|
Видеокарта |
GIGABYTE GeForce RTX 5060 Ti WINDFORCE MAX OC, 16 ГБ |
|
Память GPU в диагностике |
|
|
Процессор |
AMD Ryzen 5 5600 |
|
Оперативная память |
32 ГБ |
|
Среда |
Windows, |
|
Пакет CUDA runtime |
|
|
Агент для работы с проектом |
OpenCode |
Тестировать систему на абстрактных задачах вроде написания функций сортировки смысла не было — синтетические бенчмарки никак не отражают специфику реального продакшна.
Передо мной стояла прикладная задача: конвертировать готовую HTML-верстку в блоки Gutenberg посредством Carbon Fields в рамках моего базового плагин-шаблона. Модель должна была проанализировать архитектуру, распределить PHP-логику по файлам, зарегистрировать блок и сгенерировать осмысленные русскоязычные подписи для полей в админке.
Первый этап: скачать всё, что посоветовали нейросети
Пул кандидатов формировался с подачи ChatGPT, Claude и DeepSeek: я запрашивал кодинг-модели, способные поместиться в 16 ГБ, и скачивал релевантные варианты. В результате сформировался следующий арсенал:
|
Модель |
Какие варианты пробовал |
Первое впечатление |
|---|---|---|
|
Qwen Coder 7B семейства 2.5 |
Q4, Q8 |
Оптимальна для локальных рутинных задач, в версии Q8 размещается без проблем |
|
Qwen2.5-Coder-14B‑Instruct |
Q4, Q5 |
Разумный компромисс между габаритами и качеством |
|
Qwen3-Coder-30B‑A3B‑Instruct |
Q4, Q3 |
Q4 целиком в VRAM не влез; Q3 превзошел первоначальные ожидания |
|
Qwen3-Coder‑REAP-25B‑A3B |
Q4 |
Успешно умещается с контекстом вплоть до 32K на моей сборке |
|
DeepSeek‑Coder‑V2-Lite‑Instruct |
Q4, Q5 |
Продемонстрировала аномально низкую скорость генерации |
|
Phi-4 |
— |
Четкой роли в текущей экосистеме не нашла |
Модификации с 3–8 миллиардами параметров детальному сопоставлению в качестве основных флагманов не подвергались. Одну из 7B-версий я всё же оставил под мелкие подзадачи — для правки небольших фрагментов кода задействовать тяжеловесов избыточно.
Для тех, кто не до конца погружен в нюансы терминологии: квантование снижает разрядность весовых коэффициентов сети, экономя оперативную память. Маркировки вроде Q4, Q5 и Q8 отражают степень такого сжатия. Как правило, меньший объем влечет деградацию точности, однако оценивать модели исключительно по индексу после буквы Q некорректно.
У Qwen3-Coder присутствует индекс A3B, что указывает на архитектуру Mixture of Experts (MoE). Общее количество параметров составляет около 30 миллиардов, однако при обработке токена задействуется лишь около 3 миллиардов. Это оптимизирует вычислительные затраты, хотя требования к объему хранения весов остаются на уровне полновесных моделей. Детальные спецификации доступны в официальной карточке Qwen3-Coder.
REAP представляет собой отдельную ветку развития. Это базовая модель, усеченная путем удаления части экспертных блоков. Здесь модифицируется сама структура сети, а квантование накладывается уже поверх полученного результата. Метод подробно разобран в документации Cerebras.
Вместо «вроде быстро» — скрипт с замерами
На коротких запросах генерация происходит мгновенно, но стоит скормить нейросети объемный массив кода, как производительность резко падает. Субъективные ощущения в данном случае плохой советчик.
При содействии ChatGPT я написал скрипт на PowerShell для автоматизированного тестирования через llama-server.exe. Утилитный сценарий последовательно активировал различные размеры контекстного окна, фиксировал потребление видеопамяти через nvidia-smi и протоколировал показатели.
Цель ставилась прагматично: получить точные метрики — объем входящих токенов, задействованную память на старте и в пике, а также кадровую частоту (скорость генерации). Общее понимание уже сформировалось, а консолидированной матрицы для объективного сравнения не хватало.
Производительность отслеживалась отдельно на этапе синтаксического анализа промпта (prefill) и непосредственной генерации ответа (generation). Параллельно контролировался остаток свободной VRAM в момент максимальной нагрузки.
Физический размер файла модели на накопителе не коррелирует напрямую с аппетитами VRAM. Помимо весовых коэффициентов, аппаратные ресурсы расходуются на рабочие буферы и KV-кеш, обслуживающий контекстный массив.
Вывод скрипта содержал отдельные столбцы Context и PromptTokens. Первый параметр задавал лимит окна, второй отображал реальное количество токенов во входящем пакете. В финальном стресс-тесте для режима 32K нагрузка составляла 29 491 токен из 32 768, а для теста 48K — 44 236 из 49 152. В обоих случаях речь шла о заполнении примерно на 90%, что имитировало реальный объемный контекст, а не формальное приветствие при гигантских настройках окна.
Просто скачать подходящий по весу GGUF-файл и инициализировать его в памяти — лишь полдела. Настоящий краш-тест начинается при заполнении окна «под завязку».
Первый победитель: Qwen2.5-Coder-14B Q5
Версия 7B (Q8) была закреплена за быстрыми рутинными задачами. Полноразмерная Qwen3-Coder-30B (Q3) осталась объектом экспериментов. Вариант REAP 25B (Q4) рассматривался как перспективный претендент.
В качестве основного инструмента была утверждена Qwen2.5-Coder-14B в квантовании Q5. Она полностью устраивала меня по габаритам и качеству генерируемого кода. Казалось бы, найден идеальный баланс — можно ставить точку в поисках.
Заодно я провел ревизию локального хранилища.
Модель DeepSeek‑Coder‑V2-Lite демонстрировала нездоровую, аномальную медлительность. Причину выявить не удалось, а поскольку альтернативные варианты работали стабильнее, я просто стер её.
Phi-4 также отправилась в корзину. Это универсальный 14B-релиз с заявленным окном 16K, тогда как мне требовался узкоспециализированный помощник под конкретные архитектурные паттерны. Её характеристики описаны в репозитории Microsoft. Среди уже утвержденных фаворитов сценариев для её применения не нашлось.
Засорить диск гигабайтами GGUF-файлов под всевозможные кванты элементарно. Гораздо сложнее заполучить надежный инструмент, которому не страшно доверить продакшн-окружение.
Подключаем OpenCode — и меняем фаворита
Интеграция выбранной Qwen2.5-Coder-14B в контур OpenCode произошла быстро, но разочарование последовало незамедлительно.
На запрос создать или модифицировать файл модель могла выдать JSON-ответ прямо в чат и благополучно завершить работу. Текст присутствовал на экране. Структура проекта оставалась нетронутой.
До подключения автономного агента критерием служило качество написанного кода. Теперь планка опустилась до сурового бинарного вопроса: создан запрошенный файл в директории проекта или нет?
Агентский сценарий подразумевает, что модель корректно сформирует вызов инструмента, обработает ответ и продолжит цепочку рассуждений. Сгенерировать похожий на вызов JSON недостаточно.
Для успешного function calling должны синхронизироваться модель, шаблонизатор чата, бэкенд-сервер и клиент — об этом подробно сказано в официальной документации llama.cpp. В моей конкретной конфигурации эта связка стабильно работать отказалась.
А вот Qwen3-Coder‑REAP-25B‑A3B влилась в рабочие процессы OpenCode значительно органичнее. Она исполняла системные команды, оперировала файлами и демонстрировала отличный уровень кодинга. При этом в формате Q4 оставался достаточный резерв под 32K-контекст.
Складывалось впечатление, что идеальный инструмент наконец найден: код пишет, агентские команды отрабатывает, запас по памяти имеется. Поиски окончены — на этот раз окончательно.
Второй фаворит засыпался на русском языке
Мои блоки Gutenberg критически зависят от русскоязычных названий полей. Это ключевой элемент интерфейса: контент-менеджер должен видеть интуитивно понятные метки в административной панели.
Я не ставил перед нейросетью задачу сочинять художественную прозу. Требовалось лишь сформировать массив подписей для Carbon Fields. Казалось бы, если архитектура успешно справляется с бэкендом на PHP, проблем с базовым русским лексиконом возникнуть не должно.
Однако именно на этом рубеже REAP потерпела фиаско. Добиться стабильно чистого русского языка в заголовках не удавалось. Я корректировал системные промпты, вводил жесткие ограничения и запреты, но итоговый результат стабильно разочаровывал.
Код генерировался исправно. Инструменты вызывались. А вот на локализации полей мы зашли в тупик.
Ручное переписывание сгенерированных меток после каждого запуска не входило в мои планы.
Пришлось вернуться к полноразмерной Qwen3-Coder-30B‑A3B‑Instruct в квантовании Q3. Она мгновенно распарсила промпт и выдала корректные русскоязычные заголовки.
Оставалось лишь договориться с лимитами видеопамяти.
Q3 бывает очень разным
Полноразмерная модель 30B в первоначальной конфигурации позволяла комфортно работать с контекстом лишь в пределах 24K. Требовалось масштабирование.
Особенно показательны оказались результаты тестов стандартного пресета Q3_K_M:
|
Настроенный контекст |
Генерация |
|---|---|
|
16K |
63,8 токена/с |
|
32K |
1,57 токена/с |
При переходе к 32K скорость обвалилась практически в сорок рублей — простите, в сорок раз. Работать на скорости полтора токена в секунду не представлялось возможным, поэтому начался поиск альтернатив.
Тогда я обратил внимание на альтернативные варианты квантования от команды Unsloth:
|
Вариант Qwen3-Coder-30B‑A3B‑Instruct |
Примерный размер файла |
|---|---|
|
|
14,7 ГБ |
|
|
13,8 ГБ |
|
|
12,8 ГБ |
Метраж указан для файлов из репозитория Unsloth. Это объем файлов на SSD-накопителе, а не прямые замеры потребления VRAM.
Изначально симпатии были на стороне UD-Q3_K_XL: он обеспечивал экономию памяти относительно Q3_K_M и выглядел менее радикальным компромиссом по сравнению со зловещим суффиксом IQ3_XXS.
Но горький опыт предыдущих бенчмарков отучил меня слепо доверять буквенным индексам в названиях файлов.
Финальный замер: почти одинаковая скорость, разный запас памяти
Ниже приведены метрики двух запусков при сконфигурированном окне в 32 768 токенов и входящем потоке из 29 491 токена:
|
Метрика |
UD‑IQ3_XXS |
UD‑Q3_K_XL |
|---|---|---|
|
VRAM после загрузки, MiB* |
14 717 |
15 605 |
|
Пиковая VRAM, MiB* |
14 794 |
15 666 |
|
Прирост от загрузки до пика, MiB* |
77 |
61 |
|
Свободно на пике, MiB* |
1 517 |
645 |
|
Обработка входа, токенов/с |
1 863,13 |
1 718,98 |
|
Генерация, токенов/с |
42,32 |
42,04 |
77 MiB — это дельта между состоянием покоя после старта и пиковой нагрузкой, однако данный показатель не отражает суммарные затраты на контекст: параметр LoadedMB фиксировался уже после инициализации сервера с заданными параметрами. Таблица демонстрирует общую задействованную память GPU с учетом инфраструктурных накладных расходов.
По скорости генерации зафиксирована ничья: 42,32 против 42,04 токена в секунду.
А вот свободный буфер памяти кардинально различался: у конфигурации UD-IQ3_XXS в резерве оставалось на 872 MiB больше — 1 517 против 645 МБ. Более чем двукратное преимущество в свободном пространстве при идентичной производительности.
Реальных отличий в качестве генерации кода на моих задачах обнаружено не было. Отдавать модели UD-Q3_K_XL почти гигабайт драгоценной памяти не имело ни малейшего смысла.
А если всё‑таки попробовать 48K?
Разумеется, на этом эксперименты не прекратились: когда графический адаптер располагает полутора гигабайтами свободного пространства, возникает непреодолимое желание выжать максимум.
Вот результаты прогона на 48K:
|
Метрика |
Прогон на 48K |
|---|---|
|
Настроенный контекст |
49 152 токена |
|
Фактический вход |
44 236 токенов |
|
VRAM после загрузки |
15 878 MiB |
|
Пиковая VRAM |
15 937 MiB |
|
Прирост от загрузки до пика |
59 MiB |
|
Свободно на пике |
374 MiB |
|
Обработка входа |
1 419,72 токена/с |
|
Генерация |
22,68 токена/с |
Контекст 48K покорился, но в резерве осталось всего 374 MiB. Скорость генерации упала до 22,68 токена/с, что почти вдвое медленнее показателей UD-IQ3_XXS на 32K.
Попытка замахнуться на 65K закономерно завершилась аварийным завершением процесса по нехватке памяти. Заветные честные 64K остались излишне оптимистичной иллюзией.
Для ежедневных задач я зафиксировал планку на отметке 32K: около 42 токенов в секунду и комфортный запас прочности по VRAM. Штурмовать 48K можно, но оставлять менее 400 мегабайт буфера для стабильной продакшн-среды опрометчиво.
Финальным выбором стала следующая конфигурация:
Qwen3-Coder-30B-A3B-Instruct-UD-IQ3_XXS.gguf
Название звучит как команда терминала. Зато утилита полноценно взаимодействует с инструментами OpenCode, решает задачи по WordPress и фронтенду, а также генерирует грамотные русские подписи, на которых забуксовал REAP. Это полноценный весовой массив без вырезания экспертов, пусть и с агрессивным квантованием. После инициализации 32K-контекста остается 1 517 MiB свободного пространства — примерно 1.48 GiB чистой VRAM.
С чего я начинал бы тесты сегодня
На старте я оценивал ответы чата по умозрительным критериям качества кода, хотя фокус изначально следовало сместить на проверку агентских функций.
Теперь тестирование начиналось бы с простейшего, но комплексного кейса: прочитать файл, внести правки через инструмент, сгенерировать программный код и заполнить русскоязычные метки. Лишь прошедшие этот фильтр кандидаты должны подвергаться замерам производительности и емкости контекста.
Qwen2.5-Coder-14B устраивала по качеству кода, но провалилась в агентском контуре. REAP отлично взаимодействовала с OpenCode, но не справилась с локализацией. Полноразмерная Qwen3-Coder удовлетворила меня и по генерации, и по интеграции в пайплайн автоматизации, хотя и потребовала ювелирного подбора квантования.
Именно поэтому итоговый выбор оказался гораздо сложнее банального принципа «бери модель покрупнее в Q4».
Параллельно с тестированием моделей я постоянно дорабатывал системные промпты: объяснял архитектуру плагина, регламентировал структуру генерируемых блоков. Объем инструкций рос лавинообразно.
В итоге рабочий промпт раздулся до четырехсот строк. Блок скомпилировался без ошибок, но тут же возник закономерный вопрос: где грань между полезным сводом правил и программным кодом, который я почему-то изложил на естественном языке? Модель выбрана, теперь предстоит разобраться с этой методологической дилеммой.
В планах под текущую Qwen3-Coder-30B значится аппаратный апгрейд: рассматривается покупка второй видеокарты на 16 ГБ ради экспериментов с квантованием Q4–Q5 и расширенным контекстом. Насколько успешной окажется двухчиповая конфигурация — тема для отдельного цикла тестов.
В перспективе я планирую аналогичным образом протестировать универсальные языковые модели и vision-решения для работы с графикой. Но это уже совсем другие истории.
Первоначальный план казался банальным: подобрать модель под имеющуюся видеокарту. В итоге я подобрал модель и начал подыскивать к ней вторую видеокарту.
О подобных инженерных экспериментах, разработке под WordPress и буднях разработчика я пишу в Telegram-канале «Вла’д Лебедкин | Stack & Life». Заглядывайте, если любопытно, как локальные нейросети уживаются с инженером в тесных рамках 16 ГБ VRAM.
AMD предупредила партнеров о возможном росте цен на процессоры Ryzen на 10%
В интернет утекла информация о первом ноутбуке на неанонсированном процессоре Intel Nova Lake
Американский стартап планирует добывать уран из морской воды для обеспечения человечества энергией на 50 тысяч лет
«Яндекс» бросает вызов Microsoft Office: «Документы» теперь доступны на ПК
Мобильной GeForce RTX 5090 сняли лимиты: энергопотребление выросло до 250 Вт, а производительность — на 40%
Скорость генерации токенов на новых Mac mini с M6 и M5 Pro: ранний прогноз до релиза железа
SoftBank привлек заем на $11,87 млрд для инвестирования в OpenAI
В Китае поступил в продажу двухместный летающий «НЛО»-амфибия за $120 000