Визуализация программного кода: увидеть незримое

21 июнь, 2010 - 10:09Вячеслав Колдовский

В апреле 2010 г. исполнилось 45 лет закону Мура, который все это время надежно предсказывал удвоение вычислительной мощи компьютеров каждые полтора года. Но несмотря на рост возможностей оборудования в геометрической прогрессии, отрасль разработки ПО подобными успехами похвастаться не может, развивается она гораздо более скромными темпами. Это совершенно не означает, что программисты менее ответственно относятся к своей работе, просто они сталкиваются с абсолютно другими проблемами...

Визуализация программного кода увидеть незримое
Незатейливый интерфейс CodeCity вполне пригоден для основательного исследования самых серьезных проектов

В далеком 1975 г. увидела свет первая редакция ставшей впоследствии классической книги Фредерика Брукса (Frederick Brooks) «Мифический человеко-месяц, или Как создаются программные системы», автор которой открыл всему миру глаза на специфические проблемы, сопутствующие разработке ПО. Наверное, следует обратить внимание, что в то время компьютерные технологии сравнительно недавно вышли из научных лабораторий, развитие всего околокомпьютерного происходило сумасшедшими темпами, и многие специалисты предсказывали, что не позже 2000 г. в программировании как таковом не станет надобности, поскольку пользователям будет достаточно лишь формулировать свои желания, чтобы умные машины их исполняли. Брукс, в отличие от многих коллег-теоретиков прошедший неоценимую практическую школу IBM System 360, второго по стоимости после программы «Аполлон» американского проекта 1960-х, имел несколько иной взгляд на проблему. Не отрицая безусловного прогресса в области разработки ПО, он заметил, что на его пути имеются некоторые препятствия и преодолеть их в обозримой перспективе будет непросто. В дополняющей книгу статье «Серебряной пули нет: сущность и акциденция в программной инженерии», первоначально опубликованной в малоизвестном издании в 1986 г. и какое-то время спустя перепечатанной авторитетным журналом IEEE Computer, он выделил две группы сложностей, сопутствующих разработке ПО: акцидентные и сущностные. Первая, чье название происходит от англ. accidental, что в буквальном переводе означает «случайный», но по авторскому разъяснению больше соответствует слову «несущественный», содержит именно те препятствия, которые со временем должны исчезнуть вследствие развития компьютерных технологий. Во вторую же в качестве неразрешимых препятствий Брукс поместил несколько характеристик ПО, и одна из них, незримость, будет предметом нашего разговора.

А есть ли проблема?

Традиционно исходный код программных систем представляется в виде текстовых файлов. Как правило, основная их часть создается вручную, иногда на помощь приходят различные автоматизированные генераторы, но сути это не меняет: чтобы разобраться в коде, его необходимо как минимум прочитать. Для того чтобы хотя бы немного представить масштабы проблемы, приведем наглядный пример. Допустим, перед неким программистом стоит задача изучить код программной системы, размер которой составляет 1 млн строк (это достаточно крупный проект, но в наше время – не редкость). Пусть на чтение одной строки у него уходит в среднем три секунды, а работать он будет стандартные восемь часов в день. Выполнив простые арифметические расчеты, мы обнаружим, что всего программисту понадобится свыше ста дней, что при пятидневной рабочей неделе вплотную приближается к полугоду непрерывной работы. К тому же просто прочитать код совершенно недостаточно для того, чтобы в нем разобраться: порой запутанный участок из пары десятков строк, созданный, например, начинающим программистом, может ввести в многочасовой ступор даже весьма опытного разработчика. Соответственно, совершенно бессмысленно с помощью подобных расчетов даже пытаться оценивать время, необходимое для изучения кода программного проекта – по аналогии с тем, что прочитать книгу совсем не означает понять ее (к тому же текст программы – произведение далеко не развлекательного жанра).

Сам Брукс охарактеризовал незримость ПО как отсутствие возможности отобразить программный код в виде естественных графических представлений, подобно тому как, например, архитектор может создать модель здания еще до его постройки. В корне проблемы лежит искусственное происхождение ПО как уникального творения человека, не имеющего прямого аналога в природе. Фактически любые попытки наглядно представить программный код наталкиваются на необходимость делать это с нескольких различных точек зрения. Притом такие представления обычно недоступны неспециалисту, в отличие от того, как, скажем, модель автомобиля в масштабе 1:43 вполне позволяет составить впечатление о реальном изделии даже ребенку. Еще один, вероятно, даже самый существенный аспект незримости ПО заключается в отсутствии развитых механизмов визуального программирования, которые дали бы возможность полностью избавиться от необходимости написания кода, но при этом не сузили бы потенциал разработчика и не оказали негативного влияния на производительность его труда. Современные инструментальные средства частично восполняют данный пробел, но только применительно к достаточно узким задачам: проектированию графического интерфейса, формированию структуры БД. И наконец, нельзя обойти вниманием крайне острую проблему синхронизации исходного кода, традиционно оформленного как набор текстовых файлов, и его визуального представления. Само по себе решение этой задачи иногда бывает настолько трудоемким, что только из-за нее разработчики зачастую полностью отказываются от каких-либо попыток визуализации.

Что не так с UML?

В 1990-х в профессиональных кругах активно обсуждались перспективы универсального языка моделирования UML, разработчики которого смело утверждали, что именно он даст возможность раз и навсегда разрешить проблему визуализации программного кода. Более того, как ожидалось, строгость его описания позволит полностью перейти к визуальному программированию, оставив в прошлом необходимость создавать код в текстовом виде. Некоторое отрезвление пришло с первой официальной спецификацией языка, представленной на стандартизацию в 1997 г. Не принимая во внимание того, что первые редакции содержали множество неточностей, самым серьезным недостатком следует назвать ее сложность, в частности документ занимал 800 страниц (itc.ua/ 4754). Исправить положение обещали во второй версии, но UML 2.0 ничуть не стал проще. К примеру, только два основных документа наиболее актуальной на сегодня спецификации UML 2.3 – Infrastructure и Superstructure – аккурат укладываются в 1000 страниц, но ведь есть и другие, скажем описывающие язык OCL и правила обмена диаграммами. Для сравнения, спецификация такого современного и синтаксически богатого универсального языка программирования, как C#, занимает всего порядка 500 страниц.

Но основная проблема UML состоит не только в большом объеме спецификаций. В погоне за универсальностью его создатели, похоже, потеряли из виду, что изначально основной его задачей было облегчение разработки ПО. UML 2.3 насчитывает 14 типов диаграмм, разделенных на две группы (структурные и поведения). В реальных проектах программисты обычно применяют только небольшую часть из них, поскольку попытки провести всеобъемлющее моделирование на UML иногда обходится дороже, чем написание соответствующего кода. К тому же диаграммы UML не всегда оказываются самым наглядным представлением программных конструкций. К примеру, если диаграмма классов хорошо прижилась (в основном из-за того, что у нее не было достаточно распространенного предшественника), то диаграмма деятельности, призванная заменить привычные блок-схемы, так и не смогла полностью справиться со своей задачей.

Несмотря на все недостатки, UML получил довольно широкое распространение и занял место признанного индустриального стандарта. Однако с уверенностью можно утверждать, что всецело решить проблему визуализации программного кода и, тем более, визуального программирования ему не удалось (хотя для этого и существуют отдельные инструменты, они не завоевали большой популярности). Похоже, это именно тот случай, когда успех решения обеспечивается не столько его внутренними качествами, сколько отсутствием достойной альтернативы.

Визуализации кода в IDE

Визуализация программного кода увидеть незримое
Порой виртуальные города в CodeCity выглядят завораживающе. Знакомьтесь – jEdit, программистский текстовый редактор

В том, что IDE обрастают огромным числом инструментов, нет ничего удивительного. Показательно, что среди тенденций последнего времени весьма выделяется стремление создателей инструментальных средств наделять разработчиков все боóльшими возможностями изучения и визуализации программного кода. К примеру, в недавно увидевшей свет Microsoft Visual Studio 2010 появился такой инструмент, как Architecture Explorer, призванный анализировать сложный программный код в графической форме (ko.com.ua/44078). С его помощью можно наглядно отобразить взаимодействия и зависимости между классами проекта, непосредственно перейти к интересующему фрагменту.

Несмотря на озвученные нами недостатки, расширяется и поддержка UML – новая версия IDE от Microsoft позволяет работать с боóльшим числом диаграмм. Также еще в предыдущей версии Visual Studio 2008 появилась возможность расчета метрик (ko.com.ua/33561), представление которых в виде диаграмм и графиков значительно облегчает понимание кода в визуальной форме. Разумеется, подобные инструмен-ты выпускаются и для других IDE, к примеру, для открытой среды разработки Eclipse существует множество расширений, выполняющих схожие функции.

CodeCity: каждая программа – город

Свежий взгляд на решение проблемы визуализации кода представляет проект Ричарда Веттеля (Richard Wettel), исследователя из университета г. Лугано (Швейцария). CodeCity – это весьма оригинальная попытка представить исходный текст программы в виде модели виртуального города, элементы которого отражают программные конструкции. Каждое здание на сформированной трехмерной картинке отражает программный класс, высота здания определяется числом его методов, площадь фундамента – количеством атрибутов. Результат выглядит весьма впечатляюще – здесь и высокие небоскребы (классы с большим числом методов, но сравнительно малым количеством данных), и огромные парковки (классы, которые хранят данные, но не имеют кода), и просто основательные здания, отражающие наиболее важные классы, сочетающие большие объемы данных и кода. Виртуальный город разбит на кварталы по принадлежности классов к пакетам, а поскольку последние могут быть вложенными, то и структура кварталов в представлении города может быть довольно замысловатой. Цвет элементов также выбирается неслучайно: здания раскрашиваются в оттенках от темно-серого до светло-голубого в зависимости от количества строк кода, кварталы – от темно-серого до светло-серого в зависимости от уровня вложенности.

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

Но CodeCity не ограничивается исключительно возможностями построения модели города, инструмент обладает и дополнительными средствами анализа кода. В частности, можно построить карту дисгармонии (Disharmony Map), где виртуальные здания раскрашиваются в различные цвета в зависимости от специфической роли, которая отводится их классам-прототипам. Также можно переходить к исходному коду классов, выбирая соответствующие им виртуальные здания, равно как и получать информацию о количественных показателях (число строк кода, методов и атрибутов). Помимо прочего, CodeCity обладает удобными механизмами навигации по дереву классов и поиска необходимых программных сущностей.

В целом, несмотря на свое исследовательское происхождение, CodeCity вполне пригоден для практического использования с целью наглядного отображения внутреннего устройства программных проектов, что особенно важно для тех из них, которые измеряются многими тысячами и миллионами строк кода. В текущей реализации CodeCity существует в виде бесплатного кросс-платформенного приложения, разрешенного к свободному применению в некоммерческих целях. Поддерживаются проекты, выполненные на языках C++ и Java. Для IDE Eclipse существует основанное на исходных кодах проекта расширение Citylyzer. Загрузить приложение можно с персональной страницы его автора на сайте университета inf.usi.ch/phd/wettel.

Заключение

Поразительно, но идеи Фредерика Брукса, сформулированные в весьма далеком по меркам ИТ-индустрии прошлом, не утратили значимости и сегодня. Неправы оказались те, кто ожидал скорого появления «умных» компьютеров, которым не нужны будут программисты. Разумеется, это скорее плохо, чем хорошо, но такова реальность. Конечно, труд современного разработчика ПО и его предшественника на заре становления компьютерной эры существенно различается, однако не настолько сильно, насколько это необходимо, чтобы поспевать за возможностями вычислительных машин, умножающихся в соответствии с законом Мура. Как видно, незримость является достаточно серьезной проблемой, но непреодолимых трудностей не бывает, и, может быть, программисты из недалекого будущего смогут видеть программный код так же легко, как герои «Матрицы».

Сайт автора: koldovsky.com