Статей по теме, в том числе с примерами «потенциально плохого» кода, написано довольно много — в том числе и на Хабре. Мы в beeline cloud решили посмотреть, что на этот счет говорят научные работы и подтверждают ли они актуальность проблемы.

Изображение — Addy Mae — Unsplash
Изображение — Addy Mae — Unsplash

Термин «code smells» ввел Кент Бек еще в 2006 году. Он один из основоположников экстремального программирования и соавтор книги «Рефакторинг», написанной совместно с разработчиком и писателем Мартином Фаулером.

«Code smells» — это не явная ошибка, а скорее сигнал, указывающий на потенциальные проблемы в архитектуре или реализации.

Как неприятный запах заставляет нас задумываться о его источнике, так и «подозрительный код» говорит о том, что в программном продукте могут скрываться недочеты, усложняющие его поддержку и восприятие.

Можно выделить несколько распространенных категорий такого кода. Например, «завистливые функции», которые слишком часто обращаются к данным других объектов, или «ленивые классы», затраты на поддержку которых непропорциональны выполняемым ими задачам. Однако стоит заметить, что нет какой-то единой и общепринятой классификации «тревожных звоночков». Более того, их восприятие очень субъективно и может меняться от разработчика к разработчику.

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

А стоит ли вообще беспокоиться?

В 2013 году Айка Ямасита и Леон Мунен, специалисты из лаборатории Simula, основанной норвежским правительством и занимающейся исследованиями в области распределённых систем и программного обеспечения, провели любопытную работу. Они решили установить, насколько проблема «code smells» беспокоит разработчиков. Был проведен опрос среди 73 программистов на платформе по поиску удаленной работы. Участники представляли 29 стран, их возраст варьировался от 19 до 53 лет, а стаж — от 1 года до 30 лет. Их спрашивали, насколько они осведомлены о «тревожных звоночках», сигнализирующих о возможных проблемах в коде, какие из них считают критичными. 

Результаты оказались интересными. Треть опрошенных никогда не слышала о концепции «code smells». Лишь 18% респондентов заявили, что хорошо знакомы с идеями Кента Бека и сознательно избегают антипаттернов. Среди проблем чаще упоминался дублирующийся код, за ним следовали гигантские классы и слишком длинные методы. В целом результаты показали, что далеко не все разработчики озабочены проблемами, связанными с «подозрительным» кодом.

Можно предположить, что спустя 10 лет осведомленность специалистов о проблеме должна была вырасти. Однако исследование, проведенное в 2023 году, рисует похожую картину. Учёные из Австрии и Люксембурга проанализировали код двадцати тысяч pull-запросов из 25 популярных Java-проектов на предмет «подозрительных» составляющих. Для выявления недостатков специалисты применили достаточно известный статический анализатор — PMD. А также использовали модель GQM (Goal — Question — Metric), предложенную Виктором Бэйзилом — пионером эмпирической разработки ПО — для подбора актуальных метрик качества программного продукта. Результаты показали, что как принятые (37%), так и отклонённые (44%) запросы содержали признаки возможных проблем с кодом. Похоже, что, несмотря на прошедшее время, теория о «подозрительном коде» не стала популярнее.

Изображение — Tai Bui — Unsplash
Изображение — Tai Bui — Unsplash

Некоторые исследователи пытались не просто оценить степень знакомства инженеров с концепциями «потенциально плохого кода», но и выяснить, как разработчики воспринимают конкретные антпаттерны и какие из них считают наиболее критичными. В 2014 году, опираясь на находки коллег из Simula, подобную работу провела группа ученых из университетов Молизе, Саннио и Салерно в Италии. Сперва исследователи вручную выявили двенадцать различных «потенциальных проблем» кода в трех open source проектах: ArgoUML, Eclipse и JEdit. Затем они подготовили опросник, включив в него кусочки кода как с «подозрительными» признаками, так и без них. Респондентам предлагалось определить, видят ли они в этих фрагментах недочеты. В опросе приняли участие 34 специалиста: магистранты, разработчики и участники трех open source проектов, из которых ученые отбирали сниппеты кода для своего исследования.

Результаты показали, что большинство респондентов не считало проблемой наличие некоторых «тревожных» признаков, в частности, связанных с обширными списками параметров и «ленивыми классами» [затраты на их поддержку непропорциональны выполняемым задачам]. В то же время критичными респонденты сочли «звоночки» в наиболее сложных и длинных фрагментах кода. К серьезным недочетам они отнесли перегруженные классы, чрезмерно длинные методы и спагетти-код.

Кстати, к похожим выводам пришла группа исследователей, в которую вошли специалисты из Федерального университета Кампина-Гранди и других крупных бразильских вузов в 2016 году. В рамках исследования 75 разработчиков должны были выявить и оценить 15 различных потенциальных проблем в коде. Результаты показали, что среди участников не было единого мнения о том, что считать проблемой. Кроме того, разработчики определяли недочеты в коде совершенно разными способами.

По словам Мартина Фаулера, одно из преимуществ концепции «code smells» заключается в том, что их могут заметить неопытные разработчики, даже если не всегда понимают, как исправить проблему: «Я слышал о руководителях, которые выбирали «потенциальную проблему недели» и просили подчиненных найти ее в кодовой базе, а затем обсудить с командой. Одна проблема за раз — отличный способ обучить людей и улучшить их навыки программирования».

С другой стороны, итальянские специалисты из университетов Молизе, Саннио и Салерно отметили, что именно опыт разработчиков играет ключевую роль в идентификации антипаттернов, и сделали вывод: «Оценка качества кода и поиск потенциальных проблем — задача, которую следует поручать старшим разработчикам, а не джунам».

Не на глаз: как еще определяют «потенциально плохой код»

Существуют разные методы обнаружения «подозрительного» кода. Одним из распространенных подходов является статистический анализ, который применяется в автоматизированных системах. Эти инструменты исследуют исходный код и выделяют потенциальные проблемные места на основе заданных правил и шаблонов. Исследователи часто используют различные метрики, такие как цикломатическая сложность, количество строк кода и степень связности между объектами.

Еще одно перспективное направление в сфере идентификации «подозрительного» кода связано с применением машинного обучения. Так, исследователи из Университета Мишкольца в Венгрии в прошлом году опубликовали работу, в которой предложили методику, основанную на алгоритмах глубокого обучения и техниках балансировки данных. Алгоритмы обучали на 6,7 млн строк кода из 74 открытых проектов. После ряда тестов исследователи пришли к выводу, что предложенные модели способны выявлять потенциальные проблемы кода с большей точностью, чем решения, основанные на методе случайного леса, методе случайных соседей и других подходах.

Изображение — Battlecreek Coffee Roasters — Unsplash
Изображение — Battlecreek Coffee Roasters — Unsplash

Хотя подобные разработки выглядят весьма перспективно, здесь стоит отметить проблему воспроизводимости и достоверности исследований, связанных с выявлением и оценкой «code smells». Их результаты часто оказываются если не противоречивыми, то разнородными. В научном сообществе и среди разработчиков нет консенсуса о том, что именно считать «подозрительным кодом», а каждый исследовательский проект зачастую опирается на собственные критерии и метрики. 

Тем не менее, выход из положения, похоже, есть: можно разработать единые критерии оценки «подозрительного» кода, ориентируясь на список «code smells», предложенный все тем же Мартином Фаулером. В прошлом году так поступила группа сербских инженеров из Нови-Садского университета, предложив процедуру аннотации «подозрительного» кода для подготовки качественного свода данных и дальнейшего построения ML-моделей. В перспективе такой подход может обеспечить надежность и прозрачность результатов работы автоматизированных детекторов «code smells».

Дополнительное чтение:

  • Awesome Refactoring. Классическая курируемая подборка в стиле Awesome на GitHub. Здесь собраны сайты, статьи и книги, связанные с переработкой исходного кода программ — например, книга «Рефакторинг» Мартина Фаулера, которую мы сегодня упоминали. Кроме того, в коллекции есть статьи о том, как привести код в порядок и поддерживать тесты в «зелёном» состоянии — всё это с примерами.

  • Code Smells Catalog. Студент Вроцлавского технического университета в рамках магистерской диссертации собрал наиболее распространённые признаки «подозрительного» кода с примерами. В каталоге представлены такие антипаттерны, как Boolean Blindness, Callback Hell, Dubious Abstraction и другие. Подборка субъективна, но может быть полезна для изучения темы.

  • «Чистый код» — дискуссия на Хабре. Статья-перевод, собравшая большое количество комментариев о том, стоит ли рекомендовать книгу Роберта Мартина начинающим (да и любым другим) разработчикам. Также участники обсуждения приводят альтернативы «Чистому коду», на которые стоит обратить внимание.

beeline cloud — secure cloud provider. Разрабатываем облачные решения, чтобы вы предоставляли клиентам лучшие сервисы.

Комментарии (4)


  1. Oeaoo
    14.05.2025 14:18

    Назову это "cognitive immaturity smell". Во-первых, надо найти некий авторитет, чтобы трепетать перед ним и опираться на его видение. Во-вторых, залить динамичное, живое, субъективное "бетоном объективности".


    1. cupraer
      14.05.2025 14:18

      Среди проблем чаще упоминался дублирующийся код, за ним следовали гигантские классы и слишком длинные методы. В целом результаты показали […]

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

      В принципе, текст можно было переставать читать сразу после того, как в первом же абзаце инфоцыган Фаулер был назван «разработчиком».


  1. Dhwtj
    14.05.2025 14:18

    Исследования показали
    Исследования показали


  1. JerryI
    14.05.2025 14:18

    Без кода - жидко