Опубликован: 11.02.2005 | Доступ: свободный | Студентов: 2767 / 211 | Оценка: 4.19 / 3.88 | Длительность: 16:12:00
ISBN: 978-5-9556-0023-X
Лекция 16:

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

< Лекция 15 || Лекция 16: 123 || Лекция 17 >
Аннотация: Что нужно для переиспользования? Необходимость математической культуры. Если бы Билли остался математиком... Образцы, шаблоны и фреймы.

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

Именно это требование обычно трактуется как модульность программного изделия. Преимущества модульности, понимаемой в общем смысле это возможности замены модуля без изменения всего остального и повторного использования программных фрагментов. Последнее уже можно рассматривать как особый стиль программирования, для которого модульность является одним из средств.

Средства поддержки модульности характеризуют даже не стиль, а конкретный язык, поддерживающий этот стиль. Поэтому правомерно говорить не о стиле, а о конкретном языке, в какой мере он поддерживает модульное построение программ в рамках своего стиля.

Что нужно для переиспользования

Стиль от переиспользования характеризуется тем, что при составлении программы стремятся максимально использовать то, что уже сделано - самим программистом, его коллегами или же вообще где-либо. Давно уже общепризнано, что в идеале на смену программированию как кодированию алгоритмов должно прийти программирование как сборка из заранее заготовленных блоков - сборочное программирование. Этот термин введен в 1978 г. Г. С. Цейтин позднее отделил это понятие от теоретических рассмотрений и представил его с программистской стороны. Заметим, что математики уже давно отказались от построения новых теорем (соответствующих в информатике программам) и новых понятий (соответствующих абстрактным типам данных) с пустого места. В математике весьма профессионально переиспользуются ранее полученные результаты. Здесь из-за концептуального единства системы понятий и строгих критериев обоснованности не возникает проблемы совместимости новых версий, которая зачастую губит попытки не только переиспользования, но и просто использования старых программ.

Тем не менее интересно проделать следующий мысленный эксперимент: а что было бы, если математики работали бы примерно в таких же условиях, как программисты?

Ну, ясно, что если бы математик, опубликовавший теорему, брал бы деньги (а тем более требовал бы их заранее) за каждое ее использование, то переиспользование сразу бы си-и-ильно сократилось.

Даже если бы он не брал деньги за теорему саму по себе, но засекретил бы ее доказательство и угрожал бы уголовным преследованием всякому, кто осмелится понять (`дизассемблировать') написанный им текст, ситуация пришла бы к той же мертвой точке (здесь эта калька английского слова `deadlock' лучше русского слова `тупик').

Видимо, достаточно было бы оплачивать труд математиков на повременной основе, проверяя обоснованность отчетов о затраченном времени по числу строк написанного доказательного текста. Это, может быть, не прекратило бы переиспользование полностью, но любой математик (а не только жулики) при каждом удобном случае переписывал бы чужие доказательства своими терминами и с маленькими изменениями. Здесь к мертвой точке пришли бы медленнее, но столь же неизбежно.

Как видите, мы можем сделать важный социальный и практический вывод: единственным шансом на излечение нынешних подростковых болезней программирования является работа сообществ открытого программного обеспечения и открытой проектной документации [ 34 ] .

Понятно, что при использовании готовых строительных блоков возможны потери. Тем не менее потенциальная выгода за счет переиспользования просто колоссальна. В математике, где имеются точные оценки, показано, что длину доказательства (читай - программы) можно сократить в БАШНЮ ЭКСПОНЕНТ РАЗ без существенной потери эффективности лишь за счет введения лемм (читай - использования уже построенных программ).

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

Вторая ситуация - другая крайность. Программисту на Java потребовалось построить синтаксический анализ. На вопрос о том, как он это делает, получен ответ: "Зачем это знать? У меня есть пакет JavaCC, который все делает, как надо!" Вместе с тем, дальнейшие расспросы показали, что этот программист не представляет себе даже того, какого типа метод анализа поддерживает JavaCC, и, следовательно, ничего не может сказать о том, как задание грамматики для данного пакета связано с эффективностью анализа. Узнав возможные варианты, программист призадумался, но ничего менять не стал. Почему? Ответ простой: "Так ведь все уже работает!" Короче говоря, качество использования готовых компонентов системы зависит от знания о них.

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

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

Расшифровка предыдущего предложения позволит вдумчивому читателю самому вывести все условия, необходимые для обеспечения переиспользования в конкретной обстановке. Любые указания здесь бесполезны (если человек еще не осознал предыдущее) либо вредны (если он думает, что осознал, на самом деле ничего не понимая). Можно дать лишь общий совет для тех, кто еще занимается (само)образованием.

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

Иногда переиспользованию способствует применение развитых языковых средств. В частности, C++ и Java довольно часто позволяют переносить программы из одной операционной обстановки в другую (перенос - одна из форм переиспользования). Но те, кто реально занимался переносом программ, наверняка вспомнят при чтении предыдущего предложения досадные несоответствия, выявлению и предупреждению которых C++ и Java никак не помогают.

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

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

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

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

Применение переиспользуемых компонентов характеризуется следующими особенностями стиля:

  • главная характеристика стиля от переиспользования: предпочтение поиска кандидатов на внедрение в программу их самостоятельной разработке;
  • стремление к исследованию существующих кандидатов, к выявлению в них особенностей, полезных или вредных для решаемой задачи;
  • попытки адаптации своего решения для осуществимости внедрения (в частности, некоторые из паттернов (см. ниже) рассматривают именно те случаи, когда структуры данных Вашей программы и переиспользуемого компонента существенно различаются);
  • сопоставление и оценка вариантов внедрения и самостоятельной гипотетической разработки;
  • адаптация внедряемого в программу материала, если она требуется, что возможно лишь при двух условиях:
    • открытость программного текста;
    • наличие адекватной и открытой высокоуровневой документации к этому тексту - без нее текст программы полезен лишь для хакеров.

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

  • необходимо уделять особое внимание документированию (лучше всего, самодокументированию) переиспользуемых компонентов, причем документация должна четко выделять существенные особенности алгоритма, показывать имеющиеся призраки и использованные подпорки, таким образом, она должна быть не комментарием к тексту программы, а высокоуровневым описанием идеи и того, что оказалось необходимым для ее конкретной реализации;
  • требуется серьезный анализ того, что кандидаты на переиспользование могут быть отнесены к типовым приемам программирования, т.е. имеют достаточно широкую для использования в дальнейшем область применимости1Анализ, проведенный специалистами компании IBM, показывает, что экономически оправдано говорить о переиспользуемом компоненте, когда он будет применяться, по крайней мере в трех разработках. ;
  • нужно прорабатывать не только варианты полного переиспользования компонентов as is, но и частичного их переиспользования в виде шаблонов, готовых фрагментов и т. п., когда требуется настройка компонента;
  • необходимы спецификации как области адекватного применения компонента, так и границ применимости (вторая часть почти всегда отсутствует в нынешних спецификациях);
  • в спецификациях нужно четко отличать принципиальные моменты от подпорок и выделять призраки;
  • необходима оценка эффективности применения компонента;
  • необходима специальная забота о публикации компонента для потенциальных пользователей: они должны иметь возможность услышать о нем.
< Лекция 15 || Лекция 16: 123 || Лекция 17 >
Илья Ардов
Илья Ардов

Добрый день!

Я записан на программу. Куда высылать договор и диплом?

Дарья Федотова
Дарья Федотова