Читабельность программного кода - Блог ITVDN
ITVDN: курсы программирования
Видеокурсы по
программированию

Выбери свою IT специальность

Подписка

Читабельность программного кода

advertisement advertisement

Введение

Вам приходилось возвращаться к фрагменту кода, написанному год или месяц назад? Каково это было?  Это было просто, или приходилось вникать в код исходя из заметок? Если у Вас не получается быстро разобраться в коде и Вы задаете себе вопрос: «Что же я тогда имел ввиду?» – Вы определенно делаете что-то не так. Скорее всего, Ваш код работает правильно. И Вы знали его вдоль и поперек, когда над ним работали. Почему же Вы не можете его вспомнить сейчас? Быть может, он не был написан достаточно доступно и не соответствовал стандартам машинного кода? В этой статье Вы найдете полезную информацию о том, как научиться писать доступный не только для себя, но и для остальных разработчиков код.

Программный код


Пример использования стандарта оформления кода

Рассмотрим это на следующем примере метода в C#:

public string Transform(List<DateTime> s)

        {

            string d = null;

            foreach (DateTime kc in s)

            {

                if (kc > DateTime.Now)

                {

                    d = d + kc + "\n";

                }

                else

                {

                    d = d + "Delayed\n";

                }

            }

            return d;

        }

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

public string GetText(List<DateTime> arrivalTimes)

        {

            var stringBuilder = new StringBuilder();

            foreach (DateTime arrivalTime in arrivalTimes)

            {

                if (arrivalTime > DateTime.Now)

                {

                    stringBuilder.AppendLine(arrivalTime.ToString());

                }

                else

                {

                    stringBuilder.AppendLine("Delayed");

                }

            }

            return stringBuilder.ToString();

        }

Или если мы обратимся к оператору “?:”, мы получим: 

public string GetText(List<DateTime> arrivalTimes)

        {

            var stringBuilder = new StringBuilder();

            foreach (DateTime arrivalTime in arrivalTimes)

            {

                string message = arrivalTime > DateTime.Now ? arrivalTime.ToString() : "Delayed";

                stringBuilder.AppendLine(message);

            }

            return stringBuilder.ToString();

        }

Что произошло с кодом? Некоторые изменения сделали наш код более читабельным:

1. Имя метода получило более понятное название.

2. Мы изменили названия переменных:

1. “kc” изменена на arrivalTime,

2. “s” изменена на arrivalTimes,

3. “d” изменена на stringBuilder,

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

3. Скобки были стандартизированы.

4. Добавлены вкладки для читаемости, размещения и разметки в скобках.

5. Оператор “?:” был введен для того, чтобы сократить наш код до четырех строчек.

6. Добавлен класс StringBuilder, чтобы избежать конкатенации (“string” + “string”). Кто-то может возразить, что создание экземпляра StringBuilder будет замедлять метод из-за его распределения памяти. Но стоит помнить, что конкатенация струн создает много мусора в памяти, который вынужден чистить Garbage Collector. Считается, что ~ 5 непрерывных строк равны созданию реализации StringBuilder, так что если список состоит из пяти или более элементов, то производительность этого метода будет увеличена. А для больших коллекций этот метод будет работать в несколько раз быстрее.

Правильный способ составления кода

Давайте перейдем к другому примеру. Рассмотрим класс пользователя:

public class User

        {

            public bool HasConfirmedEmail { get; set; }

            public bool HasActiveAccount { get; set; }

            public bool IsLoggedIn { get; set; }

            public bool HasPremiumAccount { get; set; }

            public bool StatusAutoGenerated { get; set; }

            public DateTime LastStatusChange { get; set; }

            public bool SetStatus(string status)

            {

                // write to Data Base

                return true;

            }

        }

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

public string UpdateStatus(string status, User user)

        {

            if (user.HasActiveAccount)

            {

                if (user.HasConfirmedEmail)

                {

                    if (user.IsLoggedIn)

                    {

                        if (user.HasPremiumAccount)

                        {

                            if (!user.StatusAutoGenerated)

                            {

                                if (user.LastStatusChange < DateTime.Now.AddDays(-1))

                                {

                                    if (user.SetStatus(status))

                                    {

                                        return "Updated";

                                    }

                                }

                            }

                        }

                    }

                }

            }

            return "Fail";

        }

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

const string OK = "Updated";

        const string FAIL = "Fail";

        public string UpdateStatus(string status, User user)

        {

            if (!CanUpdateStatus(user)) return FAIL;

            if (!user.SetStatus(status)) return FAIL;

            return OK;

        }

        public static bool CanUpdateStatus(User user)

        {

            if (!user.IsLoggedIn) return false;

            if (!user.HasActiveAccount) return false;

            if (!user.HasConfirmedEmail) return false;

            if (!user.HasPremiumAccount) return false;

            if (user.StatusAutoGenerated) return false;

            if (!(user.LastStatusChange < DateTime.Now.AddDays(-1))) return false;

            return true;

        }

Основные изменения, внесенные в этот код, чтобы улучшить его читабельность:

  1. Static method был создан, чтобы проверить возможность обновления статуса пользователя. Это делает метод UpdateStatus более понятным с первого взгляда. Кроме того, логика метода CanUpdateStatus может быть повторно использована в других частях системы, если они являются public и static.
  2. Все " if " были заменены, чтобы уменьшить вложения. Количество скобок значительно уменьшилось, и код гораздо легче читать и компилировать. Еще одним преимуществом данного условия является его масштабируемость. Представьте себе, что класс User имеет теперь еще три свойства, которые должны быть проверены перед обновлением статуса – будут необходимы еще три "if" выписки. Теперь Вы можете добавить только три (не более) линии в методе CanUpdatedStatus.
  3. Строки, которые представляют сообщения, были удалены из тела методов и были введены в постоянные переменные. Это помогает поддерживать код, потому что независимо от числа использований кода есть только одно место, где Вы должны изменить содержание сообщения, если это необходимо. Но, на самом деле, все тексты должны быть помещены в проект внешних ресурсов.

Источник: http://blog.goyello.com/2014/12/11/clean-code/ 

КОММЕНТАРИИ И ОБСУЖДЕНИЯ
advertisement advertisement

Покупай подпискус доступом ко всем курсам и сервисам

Библиотека современных IT знаний в удобном формате

Выбирай свой вариант подписки в зависимости от задач, стоящих перед тобой. Но если нужно пройти полное обучение с нуля до уровня специалиста, то лучше выбирать Базовый или Премиум. А для того чтобы изучить 2-3 новые технологии, или повторить знания, готовясь к собеседованию, подойдет Пакет Стартовый.

Стартовый
  • Все видеокурсы на 3 месяца
  • Тестирование по 10 курсам
  • Проверка 5 домашних заданий
  • Консультация с тренером 30 мин
59.99 $
Оформить подписку
Премиум Plus
  • Все видеокурсы на 1 год
  • Тестирование по 24 курсам
  • Проверка 20 домашних заданий
  • Консультация с тренером 120 мин
  • Скачивание видео уроков
199.99 $
Оформить подписку
Базовый
  • Все видеокурсы на 6 месяцев
  • Тестирование по 16 курсам
  • Проверка 10 домашних заданий
  • Консультация с тренером 60 мин
89.99 $
Оформить подписку
Notification success