Файл: Руководство по стилю программирования и конструированию по.pdf
ВУЗ: Не указан
Категория: Не указан
Дисциплина: Не указана
Добавлен: 30.11.2023
Просмотров: 761
Скачиваний: 2
ВНИМАНИЕ! Если данный файл нарушает Ваши авторские права, то обязательно сообщите нам.
СОДЕРЖАНИЕ
782
ЧАСТЬ VII Мастерство программирования
Лучше предварять детальные комментарии многоточием:
Пример проведения различия между общим и детальными комментариями
при помощи многоточий (C++)
Общий комментарий форматируется как обычно.
// копирование всех строк таблицы,
// кроме строк, подлежащих удалению
Детальный комментарий, являющийся частью действия, описываемого общим комментарием, пред- варяется многоточием здесь…
// ... определение числа строк в таблице
…и здесь.
// ... маркирование строк, подлежащих удалению
Другой подход, который часто оказывается самым лучшим, — вынесение кода,
соответствующего общему комментарию, в отдельный метод. В идеале методы должны быть логически «плоскими»: все выполняемые в них действия должны относиться примерно к одному логическому уровню. Если в методе выполняют- ся и общие, и детальные действия, метод не является плоским. В результате выне- сения сложной группы действий в отдельный метод вы получите два логически ясных метода вместо одного логически скомканного.
Данное обсуждение общих и детальных комментариев не относится к коду с от- ступами, содержащемуся внутри циклов и условных операторов. В этих случаях часто имеется общий комментарий перед циклом и более детальные коммента- рии в коде с отступами. Логическая организация комментариев характеризуется отступами. Таким образом, вышесказанное относилось только к последователь- ным абзацам кода, когда полная операция охватывает несколько абзацев, а неко- торые абзацы подчинены другим.
Комментируйте все, что имеет отношение к ошибкам или недокументи-
рованным возможностям языка или среды Если в языке или среде есть ошиб- ка, она, вероятно, недокументирована. Даже если она где-то описана, не помеша- ет сделать это еще раз в коде. Недокументированная возможность по определе- нию не описана нигде, и ее следует задокументировать в коде.
Допустим, вы обнаружили, что библиотечный метод
WriteData( data, numItems,
blockSize ) работает неверно, если blockSize имеет значение 500. Метод прекрасно обрабатывает значения
499, 501 и все остальные, которые вы когда-либо пробо- вали, но имеет дефект, проявляющийся, только когда параметр
blockSize равен 500.
Напишите перед вызовом
WriteData(), почему вы создали специальный случай для этого значения параметра. Вот как это могло бы выглядеть:
Пример документирования кода, предотвращающего ошибку (Java)
blockSize = optimalBlockSize( numItems, sizePerItem );
>
>
>
1 ... 88 89 90 91 92 93 94 95 ... 104
ГЛАВА 32 Самодокументирующийся код
783
/* Следующий код нужен потому, что метод WriteData() содержит ошибку,
проявляющуюся, только когда третий параметр равен 500.
Значение ‘500’ ради ясности заменено на именованную константу.
*/
if ( blockSize == WRITEDATA_BROKEN_SIZE ) {
blockSize = WRITEDATA_WORKAROUND_SIZE;
}
WriteData ( file, data, blockSize );
Обосновывайте нарушения хорошего стиля программирования Если вы вынуждены нарушить хороший стиль программирования, объясните причину.
Благодаря этому программисты, исполненные благих намерений, узнают, что попытка улучшения вашего кода может привести к нарушению его работы, и не станут изменять его. Объяснение ясно скажет, что вы знали, что делаете, а не до- пустили небрежность — улучшите свою репутацию, если есть такая возможность!
Не комментируйте хитрый код — перепишите его Вот один комментарий из проекта, в котором я принимал участие:
Пример комментирования
хитрого кода (C++)
// ОЧЕНЬ ВАЖНОЕ ЗАМЕЧАНИЕ:
// Конструктор этого класса принимает ссылку на объект UiPublication.
// Объект UiPublication НЕЛЬЗЯ УНИЧТОЖАТЬ раньше объекта DatabasePublication,
// иначе программу ожидает мученическая смерть.
Это хороший пример одного из самых распространенных и опасных заблужде- ний, согласно которому комментарии следует использовать для документирова- ния особенно «хитрых» или «нестабильных» фрагментов кода. Данная идея обо- сновывается тем, что люди должны знать, когда им следует быть осторожными.
Это плохая идея.
Комментирование хитрого кода — как раз то, чего делать не следует. Коммента- рии не могут спасти сложный код. Как призывают Керниган и Плоджер, «не доку- ментируйте плохой код — перепишите его» (Kernighan and Plauger, 1978).
Исследования показали, что фрагменты исходного кода с большим чис- лом комментариев обычно включали максимальное число дефектов и отнимали бóльшую долю ресурсов, уходивших на разработку ПО (Lind and Vairavan, 1989). Ученые предположили, что программисты склонны щедро ком- ментировать сложный код.
Когда кто-то говорит: «Это по-настоящему
хитрый код,» — я слышу: «Это по-настоящему
плохой код». Если вам что-то кажется хитрым, для кого- то другого это окажется непонятным. Даже если что-то не кажется вам очень уж хитрым, другой человек, который не сталкивался с этим трюком, сочтет его очень замысловатым. Если вы спрашиваете себя: «Хитро ли это?» — это хит- ро. Всегда можно найти несложный вариант решения проблемы, поэтому пере- пишите код.
Сделайте его несколько хорошим, чтобы нужда в комментариях во- обще отпала, а затем прокомментируйте код, чтобы сделать его еще лучше.
784
ЧАСТЬ VII Мастерство программирования
Этот совет относится преимущественно к коду, который вы пишете впервые. Если вы сопровождаете программу и не имеете возможности переписывать плохой код,
комментирование хитрых фрагментов — хороший подход.
Комментирование объявлений данных
Комментарий объявления переменной описывает аспекты переменной, которые невозможно выразить в ее имени. Тща- тельно документировать данные важно: по крайней мере одна компания, изучавшая собственные методики, пришла к вы- воду, что комментировать данные даже важнее, чем процес- сы, в которых эти данные используются (SDC в Glass, 1982).
Указывайте в комментариях единицы измерения численных величин Ес- ли число представляет длину, укажите единицы представления: дюймы, футы, метры или километры. Если речь идет о времени, поясните, в чем оно выражено: в се- кундах, прошедших с 1 января 1980 года, миллисекундах, прошедших с момента запуска программы, или как-то иначе. Если это координаты, напишите, что они представляют (ширину, долготу и высоту) и в чем они выражены (в радианах или градусах), укажите систему координат и т. д. Не предполагайте, что единицы из- мерения очевидны — для нового программиста они такими не будут. Для кого-то,
кто работает над другой частью системы, они такими не будут. После значитель- ного изменения программы они тоже очевидными не будут.
Единицы измерения часто следует указывать в именах переменных, а не в ком- ментариях. Например, выражение вида
distanceToSurface = marsLanderAltitude вы- глядит корректным, тогда как
distanceToSurfaceInMeters = marsLanderAltitudeInFeet
ясно указывает на ошибку.
Указывайте в комментариях диапазоны допустимых
значений численных величин Если предполагается, что значение переменной должно попадать в некоторый диа- пазон, задокументируйте это. Одной из мощных возможно- стей языка Ada была возможность указания диапазона до- пустимых значений численной переменной. Если ваш язык не поддерживает такую возможность (а большинство язы- ков ее не поддерживает), используйте для документирования диапазона ожидае- мых значений комментарии. Например, если переменная представляет денежную сумму в долларах, укажите, что в вашем случае она должна находиться в пределах от 1 до 100 долларов. Если переменная представляет напряжение, напишите, что оно должно находиться в пределах от 105 В до 125 В.
Комментируйте смысл закодированных значений Если ваш язык поддер- живает перечисления (как C++ и Visual Basic), используйте их для выражения смысла закодированных значений. Если нет, указывайте смысл каждого значения в ком- ментариях и представляйте каждое значение в форме именованной константы, а не литерала. Так, если переменная представляет виды электрического тока, заком- ментируйте тот факт, что
1 представляет переменный ток, 2 — постоянный, а 3
— неопределенный вид.
Перекрестная ссылка О форма- тировании данных см. подраз- дел «Размещение объявлений данных» раздела 31.5. Об эф- фективном использовании дан- ных см. главы 10–13.
Перекрестная ссылка Более эффективный способ докумен- тирования диапазонов допусти- мых значений переменных —
использование утверждений в начале и в конце метода (см.
раздел 8.2).
ГЛАВА 32 Самодокументирующийся код
785
Вот пример, иллюстрирующий три предыдущих рекомендации: вся информация о диапазонах значений указана в комментариях:
Пример грамотного документирования объявлений
переменных (Visual Basic)
Dim cursorX As Integer ‘ горизонтальная позиция курсора; диапазон: 1..MaxCols
Dim cursorY As Integer ‘ вертикальная позиция курсора; диапазон: 1..MaxRows
Dim antennaLength As Long ‘ длина антенны в метрах; диапазон: >= 2
Dim signalStrength As Integer ‘ мощность сигнала в кВт; диапазон: >= 1
Dim characterCode As Integer ‘ код символа ASCII; диапазон: 0..255
Dim characterAttribute As Integer ‘ 0=Обычный; 1=Курсив; 2=Жирный; 3=Жирный курсив
Dim characterSize As Integer
’ размер символа в точках; диапазон: 4..127
Комментируйте ограничения входных данных Входные данные могут быть получены в виде входного параметра, прочитаны из файла или введены пользо- вателем. Предыдущие советы относятся к входным параметров методов в той же степени, что и к другим видам данных. Убедитесь, что вы документируете ожида- емые и неожиданные значения. Комментарии — это один из способов докумен- тирования того, что метод никогда не должен принимать некоторые данные. За- документировать диапазоны допустимых значений можно также, использовав утверждения, и тогда эффективность обнаружения ввода неверных данных заметно повысится.
Документируйте флаги до уровня отдельных би-
тов Если переменная используется как битовое поле,
укажите смысл каждого бита:
Пример документирования флагов
до уровня битов (Visual Basic)
‘ Значения битов переменной statusFlags в порядке от самого старшего
’ бита (MSB) до самого младшего бита (LSB):
’ MSB 0 обнаружена ли ошибка?: 1=да, 0=нет
’ 1-2 тип ошибки: 0=синтаксич., 1=предупреждение, 2=тяжелая, 3=фатальная
’ 3 зарезервировано (следует обнулить)
’ 4 статус принтера: 1=готов, 0=не готов
’ ...
’ 14 не используется (следует обнулить)
’ LSB 15-32 не используются (следует обнулить)
Dim statusFlags As Integer
Если бы мы писали этот пример на C++, следовало бы использовать синтаксис битовых полей — тогда значения полей были бы самодокументирующимися.
Включайте в комментарии, относящиеся к переменной, имя переменной
Если какие-то комментарии относятся к конкретной переменной, убедитесь, что вы обновляете их вместе с переменной. Помочь в этом может использование в комментариях имени переменной. Благодаря этому при поиске переменной в коде вы найдете не только ее, но и связанные с ней комментарии.
Перекрестная ссылка Об имено- вании переменных-флагов см.
подраздел «Именование пере- менных статуса» раздела 11.2.