Архив рубрики ~Лента новостей~

Сама не разберётся: мои 7 принципов генерации кода с LLM

Сама не разберётся: мои 7 принципов генерации кода с LLM
NOVOSTI

Всем привет! Меня зовут Виктор, и более трёх лет я работаю с языковыми моделями – от проприетарных решений вроде ChatGPT до open-source систем, которые можно разворачивать локально и встраивать в собственные продукты. Я застал времена жутких галлюцинаций GPT-3.5 и ждал обещанного GPT-5 – того самого почти AGI, которое, казалось, вот-вот появится.

За это время многое изменилось: появились десятки моделей, которые можно запустить даже на слабом ноутбуке, и мощные коммерческие системы, способные понимать с полуслова.

Но одно остаётся неизменным – AGI так и не случилось.

Если два года назад нам уверенно обещали, что «всё уже близко», то теперь даже крупнейшие компании признают: ждать придётся долго.

И это не плохо. Просто разработчикам, приходится учиться работать с тем, что есть, и извлекать максимум пользы из нынешних LLM.

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

На первый взгляд – ничего нового: это те же инженерные практики, которые мы применяем в обычном программировании.

Но в контексте LLM они начинают работать совсем иначе.

В этой статье я сосредотачиваюсь на задаче генерации кода – самой близкой и понятной разработчику.

Эта область особенно показательна: в ней сильнее всего проявляются ограничения моделей – трудности с контекстом, архитектурой и интеграцией кода.
Возможно, часть этих принципов уже частично реализована в инструментах вроде Cursor или GitHub Copilot, но большинство разработчиков по-прежнему работают напрямую – через GPT, DeepSeek, Qwen или локальные модели.
А с учётом ограничений по оплате и доступу к проприетарным сервисам такой способ взаимодействия, скорее всего, останется основным.
Поэтому все наблюдения, описанные ниже, относятся именно к «ручному» взаимодействию с LLM – когда разработчик сам строит диалог и управляет процессом генерации.

Принцип 1. Сначала архитектура системы – потом код

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

Перед тем как просить модель реализовать функционал, полезно сформулировать структуру: какие входные и выходные данные предполагаются, из каких элементов состоит модуль, как они связаны между собой. Не стоит сразу требовать «сгенерировать код» – сначала обсудите с моделью саму структуру, даже если вы уже её придумали. Это даст ей контекст для дальнейшей генерации и поможет вам взглянуть на архитектуру под другим углом.

Без такой подготовки модель часто начинает додумывать детали: создаёт классы, интерфейсы и зависимости, которых в проекте никогда не было. В итоге код выглядит логично, но не стыкуется с остальной системой. Поэтому стоит заранее задать архитектурные границы, в которых модель будет работать.

В научных работах этот эффект исследуется довольно активно. Подтверждено, что предоставление LLM информации об окружающей кодовой базе и её структуре заметно повышает качество результатов. Многие современные подходы основаны на поиске и систематизации нужных фрагментов из репозитория, а также на автоматическом подмешивании зависимых сигнатур в промпт [1–3].

Принцип 2. Спроектируй код – прежде чем генерировать

Этот принцип близок к первому, но фокусируется на локальном уровне. Если первый касается архитектуры всей системы или крупного блока, то здесь речь идёт о детальном планировании именно того фрагмента, который вы собираетесь сгенерировать.

Если возникает желание попросить модель «сделать всё сразу», лучше не торопиться. Двигайтесь поэтапно – так проще контролировать качество, тестировать и корректировать код. К тому же модели гораздо сложнее испортить небольшой метод, чем целый модуль.

Хороший приём – сначала попросить модель написать короткий план, псевдокод или набор сигнатур функций, а уже потом переходить к их реализации. Такой способ снижает вероятность логических ошибок и делает результат более предсказуемым.

В научной литературе подход «plan-then-generate» считается одним из наиболее перспективных. Он особенно полезен в ситуациях, когда исходные требования сформулированы не полностью – что, по сути, и является нормой при общении с LLM [4–6].

Принцип 3. Придерживайся чистой архитектуры

Самое трудное для LLM – следить за эволюцией собственного кода при работе с большими контекстами. Когда в одном методе или классе сосредоточено слишком много задач, модель теряет нить. Она начинает смешивать уровни абстракции, добавляет ненужные зависимости и в итоге создаёт код, который трудно читать, тестировать и поддерживать.

Чтобы этого избежать, достаточно соблюдать несколько простых правил.
Во-первых, избегайте всезнающих классов: каждый должен знать только о своём функционале, а всё остальное передаваться через инъекции зависимостей.
Во-вторых, один класс – одна ответственность. Остальные функции стоит вынести в отдельные утилиты или сервисы.
В-третьих, зависимости должны направляться внутрь – детали реализации внешних слоёв (интерфейс, база данных) не должны определять поведение бизнес-логики.

Если этого не делать, модель склонна объединять всё подряд. В результате рождаются классы вроде DatabaseLoggerWithUIHandler, которые и пишут в базу, и обновляют интерфейс. На вид всё выглядит “умно”, но архитектурно это катастрофа.

Мне ближе всего принципы чистой и гексагональной архитектуры – «порты и адаптеры». Но, по сути, это неважно: можно использовать любую архитектуру, главное, чтобы модель придерживалась той же дисциплины. Всё, что обеспечивает структуру и управляемость кодовой базы, помогает LLM писать лучше. Эмпирические исследования подтверждают: нарушение архитектурной чистоты ведёт к деградации кода и накоплению технического долга [7, 8].

Принцип 4. Генерируй пошагово

Даже при наличии общей структуры не стоит просить модель сразу сгенерировать весь модуль. На этом этапе у вас уже есть описание архитектуры и понимание того, за что отвечает каждый класс. Этого достаточно, чтобы двигаться постепенно – генерируя код по методу, а не целиком.

Для LLM избыточный контекст – не благо, а источник ошибок. Чем больше кода подаётся на вход, тем выше риск, что модель начнёт путаться или повторяться. Короткие шаги позволяют контролировать процесс, вовремя уточнять требования и тестировать код сразу после генерации.

Это согласуется с тем, как обучались модели: они лучше справляются с локальными задачами, чем с крупными структурами. Исследования вроде ClassEval [9] показывают, что при переходе от функций к классам точность генерации падает в разы, а пошаговый подход помогает это компенсировать. Разработчики фреймворка FunCoder [10] подтверждают: деление задачи на функции и сборка решения по частям повышает стабильность и качество.

Принцип 5. Размер кода

Хорошо написанный код – это не только читаемость, но и управляемость. В классическом программировании давно существует понятие «хорошего тона»: избегать слишком длинных методов и перегруженных классов. Сегодня это уже не просто рекомендация, а есть статистика и эмпирические доказательства.

В исследовании [11] на выборке из 784 тысяч методов показано, что оптимальная длина метода составляет не более 24 строк. Разделение больших методов на меньшие существенно снижает затраты на поддержку. Другое исследование [12], охватившее 30 проектов и 395 релизов, показало: “всезнающие классы” и длинные методы чаще содержат ошибки и сложнее в сопровождении.

LLM идеально ложатся на эту идею, потому что обучались именно на коротких и локальных примерах кода. Для себя я сделал простое правило: класс не должен содержать больше десяти методов, а метод – больше двадцати строк. Если код разрастается, значит, пора пересмотреть архитектуру и вынести избыточное в отдельные компоненты.

Принцип 6. Пиши тесты как требования к генерации

Предыдущие принципы касались контекста и структуры, но сами требования к коду часто формулируются слишком неформально: «сделай функцию, которая…», «учти крайний случай…». Модель может понять это как угодно. Гораздо надёжнее использовать тесты.

На практике это значит следующее: сначала просите модель сгенерировать юнит-тест, описывающий поведение, а затем уже код, проходящий этот тест. Такой подход не только формализует задачу, но и резко снижает вероятность логических ошибок.

Исследования подтверждают эффективность TDD в связке с LLM. Добавление тестов до генерации повышает точность выполнения задач на 15–18% для GPT-4, а у открытых моделей вроде Llama-3 – до 38% [13]. Фактически это позволяет сократить разрыв между проприетарными и open-source-моделями только за счёт правильной методики.

Принцип 7. Проси комментарии и докстринги

Модель может генерировать синтаксически правильный код, который логически не решает задачу. Чтобы избежать этого, стоит добавить в процесс генерации дополнительный уровень размышления – попросить LLM сопровождать код короткими объяснениями.

Когда модель вынуждена пояснять свои действия, она фактически использует встроенную цепочку рассуждений. Вероятность ошибок снижается, а сам код становится понятнее. В моей практике это один из самых простых и эффективных способов стабилизировать результат: если перед генерацией попросить модель описать, почему следующие строки будут такими, итоговый код получается аккуратнее и лучше отражает замысел.

Исследование [14] подтверждает этот эффект: генерация комментариев повышает pass@k на бенчмарках MBPP и HumanEval, а в некоторых случаях даже превосходит традиционный подход chain-of-thought.

Без чёткого плана генерации почти всегда получается не то, что хотелось. Подход “сгенерируй что-нибудь рабочее” приводит к усложнению – не потому, что LLM «глупая», а потому, что она не знает ваших намерений. Механизмы уточнений и активной обратной связи только начинают появляться, поэтому пока самый надёжный способ – самому быть архитектором, аналитиком и заказчиком, а модель использовать как исполнителя, которому вы чётко ставите задачу.

Если тема кажется вам интересной, я продолжаю разбирать подобные вещи у себя в Telegram короткими постами, экспериментами и примерами из практики: «надо разобраться | заставляем LLM работать».

Изначально я планировал собрать под каждый принцип отдельный список ссылок, но оказалось, что все они тесно связаны между собой. На практике они образуют единый пайплайн – от проектирования до тестирования и документирования. Поэтому ниже – общая библиография, на которую опираются все принципы.

  1. Self-planning Code Generation with Large Language Models – самопланирование генерации кода с использованием LLM

  2. Sketch Then Generate: Providing Incremental User Feedback and Guiding LLM Code Generation through Language-Oriented Code Sketches – об эффективности подхода «сначала план — затем генерация»

  3. Planning In Natural Language Improves LLM Search For Code Generation – об эффективности генерации множества планов и выбора из них оптимального для кодогенерации.

  4. 𝖢𝗈𝖽𝖾𝖯𝗅𝖺𝗇: Repository-level Coding using LLMs and Planning – о кодировании с LLM на уровне репозитория, в том числе миграция кода на другие языки

  5. ChatCoder: Human-in-loop Refine Requirement Improves LLMs’ Code Generation – о планировании требований к коду в цикле «человек-LLM»

  6. Enhancing Repository-Level Code Generation with Integrated Contextual Information – о интеграции в промпт информации из больших репозиториев о связях на уровне типов/классов/интерфейсов/структур, показывающие, какие типы упоминаются и требуются другим типом или функцией.

  7. Design First, Code Later: The AI Era Mantra – о различных архитектурах в виде краткой справки.

  8. Evolution patterns of software-architecture smells: An empirical study of intra- and inter-version smells – это не про LLM, но принцип тот же. Работа о том, что нарушение принципов архитектурной чистоты ведет к деградации кодовой базы продукта, снижению качества самого продукта и наращиванию технического долга. Ровно то, что произойдет, если не требовать от LLM придерживаться принципов вашего проекта при генерации кода.

  9. Evaluating Large Language Models in Class-Level Code Generation – о разнице в эффективности между генерацией методов и классов, насколько падает производительность и метрики

  10. Divide-and-Conquer Meets Consensus: Unleashing the Power of Functions in Code Generation – фреймворк помогает модели вводить вспомогательные функции и писать решение по частям, а затем собирать итог.

  11. An Empirical Study on Maintainable Method Size in Java – исследования о том, что проектирование методов не более чем в 24 строки помогают снизить будущие расходы на сопровождение кода.

  12. On the diffuseness and the impact on maintainability of code smells: a large scale empirical investigation – масштабное исследование по 13 различным «запахам» кода и их влиянии на качество кода и последующее его обслуживание.

  13. Test-Driven Development for Code Generation – о влиянии практики TDD на генерацию кода.

  14. Comments as Natural Logic Pivots: Improve Code Generation via Comment Perspective – о влиянии генерации встроенных комментариев на эффективность генерации кода.

Источник: habr.com

Оцените материал:

Поделиться
Понравилась статья? Расскажите другим
ВКонтакте
Читайте также
Новости робототехники Почему искусственный интеллект является безопасностью рабочей площадки Новости робототехники Сегодня ночью украинские БЭКи атаковали район Геленджика, рядом с Новороссийском Архив рубрики ~Обо всем~ Лидеры в области качества предостерегают от оцифровки неэффективных процессов. Архив рубрики ~Обо всем~ Огромный декагон сформировался вокруг южного полюса Сатурна. Атмосферная волна появилась недавно Новости робототехники Датчики давления могут повысить точность захвата роботов. Новости робототехники Компания Poseidon Aerospace привлекла 60 миллионов долларов перед первым испытательным полетом без пилота. Архив рубрики ~Коротко из Telegram~ Телевизоры LG могут следить за тем, что происходит у вас… Архив рубрики ~Коротко из Telegram~ Крошечная open‑source‑модель MiniCPM5-2B обошла конкурентов до 4B параметров ⚡ Канал… Архив рубрики ~Коротко из Telegram~ Бесплатная обработка голоса в аудио Если записываешь голос на встроенный… Архив рубрики ~Обо всем~ Конец универсального диагноза болезни Паркинсона: почему 2026 год станет годом, когда неврология перейдет на высокоточное исследование. Архив рубрики ~Коротко из Telegram~ Дата-центр Stargate в Абилине назвали «местом рождения AGI» Глава Crusoe… Архив рубрики ~Коротко из Telegram~ Небольшой дайджест — коротко о найденных новостях 1️⃣ Российский облачный… Архив рубрики ~Коротко из Telegram~ Офлайн-ИИ на вашем телефоне В новых айфонах и топовых Android-флагманах… Архив рубрики ~Коротко из Telegram~ Почему видео от нейросети выглядит «мёртво» — и как это… Новости робототехники Почему искусственный интеллект является безопасностью рабочей площадки Новости робототехники Сегодня ночью украинские БЭКи атаковали район Геленджика, рядом с Новороссийском Архив рубрики ~Обо всем~ Лидеры в области качества предостерегают от оцифровки неэффективных процессов. Архив рубрики ~Обо всем~ Огромный декагон сформировался вокруг южного полюса Сатурна. Атмосферная волна появилась недавно Новости робототехники Датчики давления могут повысить точность захвата роботов. Новости робототехники Компания Poseidon Aerospace привлекла 60 миллионов долларов перед первым испытательным полетом без пилота. Архив рубрики ~Коротко из Telegram~ Телевизоры LG могут следить за тем, что происходит у вас… Архив рубрики ~Коротко из Telegram~ Крошечная open‑source‑модель MiniCPM5-2B обошла конкурентов до 4B параметров ⚡ Канал… Архив рубрики ~Коротко из Telegram~ Бесплатная обработка голоса в аудио Если записываешь голос на встроенный… Архив рубрики ~Обо всем~ Конец универсального диагноза болезни Паркинсона: почему 2026 год станет годом, когда неврология перейдет на высокоточное исследование. Архив рубрики ~Коротко из Telegram~ Дата-центр Stargate в Абилине назвали «местом рождения AGI» Глава Crusoe… Архив рубрики ~Коротко из Telegram~ Небольшой дайджест — коротко о найденных новостях 1️⃣ Российский облачный… Архив рубрики ~Коротко из Telegram~ Офлайн-ИИ на вашем телефоне В новых айфонах и топовых Android-флагманах… Архив рубрики ~Коротко из Telegram~ Почему видео от нейросети выглядит «мёртво» — и как это…