Чистый код. Создание, анализ и рефакторинг - [21]

Шрифт
Интервал



Аргументы усложняют функции и лишают их значительной части концептуальной мощи. Именно по этой причине я почти полностью избавился от них в этом примере. Возьмем хотя бы переменную StringBuffer. Ее можно было бы передать в аргументе (вместо того, чтобы делать ее переменной экземпляра), но тогда читателям кода пришлось бы интерпретировать ее каждый раз, когда она встречается в коде. Когда вы читаете историю, рассказываемую модулем, вызов includeSetupPage() выглядит намного более понятным, чем вызов includeSetupPageInto(newPageContent). Аргумент и имя функции находятся на разных уровнях абстракции, а читателю приходится помнить о подробностях (то есть StringBuffer), которые на данный момент не особенно важны.

Аргументы создают еще больше проблем с точки зрения тестирования. Только представьте, как трудно составить все тестовые сценарии, проверяющие правильность работы кода со всеми комбинациями аргументов. Если аргументов нет — задача тривиальна. При одном аргументе все обходится без особых сложностей. С двумя аргументами ситуация усложняется. Если же аргументов больше двух, задача тестирования всех возможных комбинаций выглядит все более устрашающе.

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

Если уж обойтись без аргументов никак не удается, постарайтесь хотя бы ограничиться одним входным аргументом. Смысл вызова SetupTeardownIncluder.render(pageData) вполне прозрачен — понятно, что мы собираемся сгенерировать данные для объекта pageData.

Стандартные унарные формы

Существует два очень распространенных случая вызова функции с одним аргументом. Первая — проверка некоторого условия, связанного с аргументом, как в вызове boolean fileExists("MyFile"). Вторая — обработка аргумента, его преобразование и возвращение. Например, вызов InputStream fileOpen("MyFile") преобразует имя файла в формате String в возвращаемое значение InputStream. Выбирайте имена, которые четко отражают различия, и всегда используйте две формы в логически непротиворечивом контексте. (См. далее «Разделение команд и запросов»).

Несколько менее распространенным, но все равно очень полезным частным случаем функции с одним аргументом является событие. В этой форме имеется входной аргумент, а выходного аргумента нет. Предполагается, что программа интерпретирует вызов функции как событие и использует аргумент для изменения состояния системы, например, void passwordAttemptFailedNtimes(int attempts). Будьте внимательны при использовании данной формы. Читателю должно быть предельно ясно, что перед ним именно событие. Тщательно выбирайте имена и контексты.

Старайтесь избегать унарных функций, не относящихся к этим формам, например void includeSetupPageInto(StringBuffer pageText). Преобразования, в которых вместо возвращаемого значения используется выходной аргумент, сбивают читателя с толку. Если функция преобразует свой входной аргумент, то результат должен передаваться в возвращаемом значении. В самом деле, вызов StringBuffer transform(StringBuffer in) лучше вызова void transform(StringBuffer out), даже если реализация в первом случае просто возвращает входной аргумент. По крайней мере она соответствует основной форме преобразования.

Аргументы-флаги

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

В листинге 3.7 у нас нет выбора, потому что вызывающая сторона уже передает этот флаг, а я хотел ограничить область переработки границами функции. Тем не менее вызов метода render(true) откровенно сбивает с толку бедного читателя. Если навести указатель мыши на вызов и увидеть render(boolean isSuite), ситуация слегка проясняется, но ненамного. Эту функцию следовало бы разбить на две: renderForSuite() и renderForSingleTest().

Бинарные функции

Функцию с двумя аргументами понять сложнее, чем унарную функцию. Например, вызов writeField(name) выглядит более доступно, чем writeField(outputStream, name)[17]. Хотя смысл обеих форм понятен, первая форма просто проскальзывает под нашим взглядом, моментально раскрывая свой смысл. Во второй форме приходится сделать непродолжительную паузу, пока вы не поймете, что первый параметр должен игнорироваться. И конечно, это в конечном итоге создает проблемы, потому что никакие части кода игнорироваться не должны. Именно в проигнорированных частях чаще всего скрываются ошибки.

Конечно, в некоторых ситуациях форма с двумя аргументами оказывается уместной. Например, вызов Point p = new Point(0,0); абсолютно разумен. Точка в декартовом пространстве естественным образом создается с двумя аргументами. В самом деле, вызов new Point(0) выглядел бы довольно странно. Однако два аргумента в нашем случае являются упорядоченными компонентами одного значения! Напротив, outputStream и name не имеют ни естественной связи, ни естественного порядка.


Еще от автора Роберт Сесил Мартин
Чистая архитектура. Искусство разработки программного обеспечения

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


Чистый Agile. Основы гибкости

Прошло почти двадцать лет с тех пор как появился Манифест Agile. Легендарный Роберт Мартин (Дядя Боб) понял, что пора стряхнуть пыль с принципов Agile, и заново рассказать о гибком подходе не только новому поколению программистов, но и специалистам из других отраслей. Автор полюбившихся айтишникам книг «Чистый код», «Идеальный программист», «Чистая архитектура» стоял у истоков Agile. «Чистый Agile» устраняет недопонимание и путаницу, которые за годы существования Agile усложнили его применение по сравнению с изначальным замыслом. По сути Agile — это всего лишь небольшая подборка методов и инструментов, помогающая небольшим командам программистов управлять небольшими проектами,… но приводящая к большим результатам, потому что каждый крупный проект состоит из огромного количества кирпичиков.


Идеальный программист. Как стать профессионалом разработки ПО

Всех программистов, которые добиваются успеха в мире разработки ПО, отличает один общий признак: они больше всего заботятся о качестве создаваемого программного обеспечения. Это – основа для них. Потому что они являются профессионалами своего дела.В этой книге легендарный эксперт Роберт Мартин (более известный в сообществе как «Дядюшка Боб»), автор бестселлера «Чистый код», рассказывает о том, что значит «быть профессиональным программистом», описывая методы, инструменты и подходы для разработки «идеального ПО».


Рекомендуем почитать
Графика DirectX в Delphi

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


Вторая жизнь старых компьютеров

Сейчас во многих школах, институтах и других учебных заведениях можно встретить компьютеры старого парка, уже отслужившие свое как морально, так и физически. На таких компьютерах можно изучать разве что Dos, что далеко от реалий сегодняшнего дня. К тому же у большинства, как правило, жесткий диск уже в нерабочем состоянии. Но и выбросить жалко, а новых никто не дает. Различные спонсоры, меценаты, бывает, подарят компьютер (один) и радуются, как дети. Спасибо, конечно, большое, но проблемы, как вы понимаете, этот компьютер в общем не решает, даже наоборот, усугубляет, работать на старых уже как-то не хочется, теперь просто есть с чем сравнивать.


DirectX 8. Начинаем работу с DirectX Graphics

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


Симуляция частичной специализации

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


Обработка событий в С++

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


Питон — модули, пакеты, классы, экземпляры

Python - объектно-ориентированный язык сверхвысокого уровня. Python, в отличии от Java, не требует исключительно объектной ориентированности, но классы в Python так просто изучить и так удобно использовать, что даже новые и неискушенные пользователи быстро переходят на ОО-подход.


В работу с головой. Паттерны успеха от IT-специалиста

Не можете сосредоточиться на работе? Постоянно отвлекаетесь на проверку электронной почты, социальные сети и новостные ленты? Пора воспользоваться советами от ведущих IT-специалистов и погрузиться в работу с головой.Освойте один из самых ценных навыков – умение сосредоточиться на сложной задаче, не отвлекаясь на мелочи. Только так можно справиться со сложной информацией и добиться лучших результатов за минимальное время. Погружение в работу – это суперсила в нашей все более конкурентной экономике XXI века.


SQL: быстрое погружение

Что общего между самыми востребованными профессиями и стремительным увеличением количества информации в мире? Ответ: язык структурированных запросов (SQL). SQL — рабочая лошадка среди языков программирования, основа основ для современного анализа и управления данными. Книга «SQL: быстрое погружение» идеальна для всех, кто ищет новые перспективы карьерного роста; для разработчиков, которые хотят расширить свои навыки и знания в программировании; для любого человека, даже без опыта, кто хочет воспользоваться возможностями будущего, в котором будут править данные.


Изучаем Python

Книга "Изучаем Python" - это ускоренный курс, который позволит вам сэкономить время и сразу начать писать работоспособные программы (игры, визуализации данных, веб-приложения и многое другое). Хотите стать программистом? В первой части книги вам предстоит узнать о базовых принципах программирования, познакомиться со списками, словарями, классами и циклами, вы научитесь создавать программы и тестировать код. Во второй части книги вы начнете использовать знания на практике, работая над тремя крупными проектами: создадите собственную "стрелялку" с нарастающей сложностью уровней, займетесь работой с большими наборами данных и освоите их визуализацию, и, наконец, создадите полноценное веб-приложение на базе Django, гарантирующее конфиденциальность пользовательской информации. Если вы решились разобраться в том что такое программирование, не нужно ждать.


Грокаем алгоритмы. Иллюстрированное пособие для программистов и любопытствующих

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