Правила написания хороших функций и структура кода

Имена переменных, методов и классов.

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

Выбирайте имена, так, чтобы они не в водили в заблуждение читателя кода. Если переменная называется accountList, читатель кода подсознательно считает что данная переменная хранит список. Если это не так, лучше назвать переменную просто accounts. По настоящему устрашающий пример дизинформации — использование в качестве имени переменной строчной L и прописной O, потому, что эти буквы почти не отличаются от констант 1 и 0.

Остерегайтесь мало заметных различий в именах.

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

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

Выбирайте имена, удобные для поиска. Одно-двух буквенные имена сложно искать, так как поиск находит их в составе других имен. Длинна кода должна соответствовать размеру его области видимости.

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

Имена классов должны представлять из себя существительные или их сочетания, но никак не глаголы. Старайтесь не использовать в именах классов такие слова как Manager, Info, Data, Processor.

Имена методов должны быть глаголами и глагольными сочетаниями.

Выберите одно слово для представления одной абстрактной концепции и придерживайтесь его.

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

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

Не добавляйте избыточный контекст. Не включайте в имя больше контекста чем необходимо.

Правила написания хороших функций и структура кода

Функция должна быть компактной, даже очень маленькой. Желательно чтобы длинна функции не превышала 20 строк.

Функции не должны содержать вложенных структур, так как это приводит к их увеличению и усложняет понимание работы функции.

Функция должна выполнять только одну операцию. Она должна выполнять ее хорошо, и ничего другого она делать не должна.

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

Под одной операцией понимается набор действий, находящихся на одном уровне абстракции.

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

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

Чтение кода сверху вниз: за каждой функцией должны следовать функции следующего уровня абстракции (вертикальное форматирование).

Каждая группа строк представляет законченную мысль. Эти мысли следует отделять друг от друга пустыми строками.

Концепции, тесно связанные друг с другом должна находится поблизости друг от друга по вертикали.

Команда switch допустима, если она встречается лишь раз в программе, используется для создания полиморфных объектов и скрывается за отношениями наследования, чтобы оставаться невидимой для остальных частей системы.

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

Наличие более двух аргументов функции усложняет написание тестов.

Если функция должна получать более двух параметров, вероятно имеет смысл упаковать некоторые из аргументов в отдельных класс, тем самым сократив количество передаваемых параметров.
Пример:
makeCircle (x, y, radius);
makeCirlce(center, radius);

Аргументы-флаги недопустимы. Передача логического значения функции говорит о том, что функция выполняет более одной операции.

Функция либо изменяет состояние объекта либо возвращает информацию о нем. Совмещение двух операций приводит к путанице.

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

Тела блоков try и catch рекомендуется выделять в отдельные функции. Обработка ошибок — это одна операция. Значит функция обрабатывающая ошибки ничего другого делать не должна.

Не возвращайте и не передавайте в вызове функции значение null. Это заставляет делать дополнительные проверки в вызывающем коде. Вместо null лучше вернуть исключение либо объект паттерна «особый случай».

Переменные следует объявлять как можно ближе к их использованию. В коротких функциях локальные переменные следует перечислять в начале каждой функции. Переменные экземпляров наоборот следует объявлять в начале класса.

Объекты предоставляют поведение и скрывают данные. Структуры предоставляют данные но лишены сколько нибудь значимого поведения.

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

Если нужна гибкость в расширении поведения, то лучше использовать типы данных и процедуры. Объектно-ориентированный код усложняет добавление новых функций, так как для этого должны изменится все классы.

Наши рекомендации