Проблема в том, что возникновение грязи, как и тупики, неизбежно. Опыт и благоразумие помогут вам избегать его, но рано или поздно вы примете решение, которое заведет вас в грязь.
Возникновение грязи весьма коварно. Вы создаете решение простой задачи, всеми силами стремясь к тому, чтобы код оставался простым и чистым. С ростом масштаба и сложности задачи вы расширяете ее кодовую базу, по возможности стараясь сохранять ее чистоту. В какой-то момент вы понимаете, что изначально приняли неверное архитектурное решение и ваш код плохо масштабируется в направлении смещения требований.
Здесь и находится критическая точка! Вы все еще можете вернуться и исправить архитектуру. Но вы также можете продолжить движение вперед. Кажется, что возврат обойдется слишком дорого, потому что вам придется перерабатывать существующий код, однако в будущем он обойдется еще дороже. Если вы будете двигаться вперед, то система сползет в грязь, и вполне возможно, что она из нее уже не выберется.
Профессионалы опасаются грязи намного сильнее, чем тупиков. Они всегда обращают внимание на грязь, которая начинает неограниченно разрастаться, и прикладывают все необходимые усилия к ее устранению – по возможности раннему и быстрому.
Движение вперед по грязи (когда вы знаете, что это грязь) является худшей из разновидностей инверсии приоритетов. Двигаясь вперед, вы обманываете себя, обманываете вашу группу, обманываете свою компанию и заказчиков. Вы говорите им, что все будет хорошо, хотя на самом деле вы ведете их к общей катастрофе.
Профессиональные разработчики серьезно относятся к управлению своим временем и концентрацией. Они понимают соблазн инверсии приоритетов и борются с ним, поскольку это является делом чести. Они непредвзято относятся к альтернативным решениям. Они никогда не увлекаются решением настолько, что не могут отказаться от него. А еще они всегда следят за возможным возникновением грязи и вычищают ее при первых признаках. Нет более печального зрелища, чем группа разработчиков, бесцельно плетущаяся по постоянно углубляющейся трясине.
Оценка – одно из самых простых, но при этом самых рискованных задач, с которыми сталкиваются профессиональные разработчики. От оценки напрямую зависит коммерческая ценность проекта. От нее зависят наши репутации. Неверные оценки становятся причиной наших страхов и провалов. Оценка – это первый клин, вбиваемый между бизнесменами и разработчиками. Это источник почти всего недоверия, связанного с этими отношениями.
В 1978 году я был ведущим программистом для 32-килобайтной встроенной программы Z-80, написанной на языке ассемблера. Программа «прошивалась» на 32 перепрограммируемых микросхемах, которые вставлялись в три платы (до 12 микросхем на каждой).
У нас в эксплуатации были сотни устройств, установленных на центральных телефонных станциях по всем Соединенным Штатам. Каждый раз, когда мы исправляли ошибку или добавляли новую функцию, нам приходилось отправлять техников к каждому устройству для замены всех 32 микросхем!
Это был настоящий кошмар. Микросхемы и платы были непрочными, контакты на микросхемах гнулись и ломались. Нечаянные изгибы плат могли повредить места пайки. Риск ошибок и поломок был огромен, а затраты для компании – слишком высоки.
Мой начальник Кен Файндер пришел ко мне и попросил что-нибудь сделать. Нам был нужен способ замены микросхем, который бы не требовал замены всех остальных микросхем. Если вы читали мои книги или слушали мои лекции, то вы знаете, что я много говорю о возможности независимого развертывания. Именно тогда я впервые усвоил этот урок.
Проблема заключалась в том, что программа представляла собой единый скомпонованный исполняемый файл. Добавление новой строки кода приводило к изменению адресов всех последующих строк. Так как в каждой микросхеме попросту хранился один килобайт адресного пространства, то изменялось содержимое практически всех микросхем.
Решение было довольно простым. Микросхемы нужно было изолировать друг от друга. Содержимое каждой микросхемы преобразовывалось в независимую единицу компиляции, которая могла записываться независимо от всех остальных.
Я определил размеры всех функций в приложении и написал простую программу, которая «укладывала» их, словно фрагменты головоломки, на микросхемах, оставляя 100 байт свободного пространства для расширения. В начале каждой микросхемы размещалась таблица указателей на все функции данной микросхемы. Во время загрузки эти указатели перемещались в память. Весь код системы был изменен таким образом, чтобы функции никогда не вызывались напрямую – только через векторы, хранящиеся в памяти.
Читать дальше
Конец ознакомительного отрывка
Купить книгу