Добавил:
Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
Роджерсон Д. - Основы COM - 2000.pdf
Скачиваний:
410
Добавлен:
13.08.2013
Размер:
2.4 Mб
Скачать

21

мира, когда, например, Вы можете редактировать электронную таблицу из текстового процессора. Реализация связывания и внедрения объектов, созданная в Microsoft, получила название OLE. Первая версия OLE для связи между клиентом и компонентом использовала аппарат, известный как динамический обмен данными (dynamic data exchange — DDE). В OLE 1 не было СОМ. DDE был построен на основе архитектуры передачи сообщений Windows. Самое лучшее, что я могу сказать об OLE 1, — этот инструмент работает, точнее, более или менее работает. DDE медлителен. Написать корректно работающий код DDE сложно. Вдобавок, DDE не слишком надежен и гибок. Излишне говорить, что требовалось изобрести что-нибудь получше.

Решением стала СОМ. СОМ меньше, быстрее, гибче, надежнее DDE. Вторая версия OLE была переписана с использованием СОМ вместо DDE. СОМ стала новым фундаментом, на котором выстроены конструкции OLE. Однако OLE — первая система на основе СОМ, и уже поэтому она не дает лучший пример использования возможностей СОМ. У OLE репутация сложного, медленного и трудного для программирования аппарата. Это недостатки реализации, а не СОМ.

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

Создатели OLE старались реализовать все возможности без каких-либо ограничений. Вместо того, чтобы вынуждать клиента и компонент установить ограниченную связь, OLE определяет избыточную связь. Компонент может делать практически все, что угодно, а клиент должен быть к этому готов. Это делает OLE очень трудным для программирования.

Скоро появятся новые продукты Microsoft на основе СОМ, и некоторые из них просто изумительны. Несомненно, другие разработчики тоже пишут компоненты СОМ. СОМ ждет блестящее будущее!

Заключительные замечания о компонентах

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

СОМ определяет стандартный способ написания компонентов. Компоненты, написанные в соответствии со стандартом СОМ, можно объединять в приложение. При этом не имеет значения, кем они написаны и как реализованы. Компонент СОМ можно использовать вместе с другими компонентами. Ключевой момент в обеспечении взаимозаменяемости компонентов — инкапсуляция. СОМ обеспечивает ее, уделяя основное внимание соединению, или интерфейсу между компонентом и клиентом. В следующей главе мы увидим, почему для компонентов так важны интерфейсы. Мы также посмотрим, как реализуется интерфейс СОМ.

2 глава

Интерфейс

Несколько лет назад «космический челнок» «Атлантис» состыковался с российской орбитальной станцией «Мир». Американцы установили на свой корабль российский стыковочный узел, подходящий к соответствующему узлу станции. Только представьте, что Вы могли бы сделать с таким стыковочным узлом! Его можно установить на Вашем доме, и туда мог бы пристыковаться космический корабль. Вы могли бы установить этот узел на старый «Фольксваген», на башню «Космическая игла» в Сиэтле или на свой гараж — и «челнок» мог бы стыковаться и с ними. Пока узел не изменился и пока установлен на корабле, космический аппарат может стыковаться с чем угодно. Имея два узла, Вы могли бы пристыковать свой «Фольксваген» к дому, а не ставить его в гараж. Не правда ли, забавно!

Стыковочный узел — это пример интерфейса (interface). Интерфейс обеспечивает соединение двух разных объектов. Хотя стыковочные узлы отлично соединяют друг с другом космические корабли, они не слишком годятся для соединения частей компьютерной программы. Для стыковки в компьютерных программах применяются наборы функций. Именно такие наборы и определяют интерфейс между разными частями программы.

Интерфейс DLL — это набор функций, экспортируемых ею. Интерфейс класса С++ — это набор членов данного класса. Однако когда в этой книге я употребляю слово интерфейс, имеется в виду интерфейс СОМ, а не все прочие. Интерфейс СОМ также включает в себя набор функций, которые реализуются компонентами и используются клиентами. Но СОМ дает более точное определение интерфейса. В СОМ интерфейсом является определенная структура в памяти, содержащая массив указателей на функции. Каждый элемент массива содержит адрес функции, реализуемой компонентом. С точки зрения СОМ интерфейсом является упомянутая структура в памяти; все остальное — это детали реализации, которые СОМ не касаются. Мы остановимся на этой структуре в конце главы, после того как посмотрим на ее реализацию с помощью С++.

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

Давайте более подробно рассмотрим роль интерфейсов в СОМ. Затем реализуем один интерфейс. После этого внимательно присмотримся к некоторым интересным деталям интерфейсов. И, наконец, разберем структуру блока памяти, соответствующего интерфейсу в смысле СОМ.

Интерфейсы — это все

В СОМ интерфейсы — это все. Для клиента компонент представляет собой набор интерфейсов. Клиент может взаимодействовать с компонентом СОМ только через интерфейс. Как мы увидим далее, клиент очень мало знает о компоненте в целом. Часто ему даже не известны все интерфейсы, которые тот поддерживает.

На рисунках в гл. 1 были представлены приложения, построенные из компонентов (эти рисунки напоминают левую часть рис. 2-1). Они могут ввести Вас в заблуждение, так как подчеркивают важность компонентов и не обращают внимания на интерфейсы. С точки зрения программиста СОМ, интерфейсы — важная часть любого приложения. Компоненты сами по себе есть просто детали реализации интерфейсов. Правая часть рис. 2-1 более точно отражает значение интерфейсов для программ СОМ.

Повторное использование архитектур приложений

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

24

 

 

Компоненты

 

 

 

 

Интерфейсы

 

Компонент A

 

Компонент C

 

 

 

 

 

 

 

-C

 

 

 

 

 

 

 

 

 

 

 

 

 

 

A

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

A

 

 

Интерфейс

 

 

C

 

 

 

Компонент B

 

Компонент D

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

Компонент E

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

Интерфейс A-B

 

 

 

Интерфейс C-D

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

B-D

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

Интерфейс

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

B

 

 

 

 

D

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

Интерфейс B-E

 

 

 

Интерфейс D-E

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

E

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

Рис. 2-1 В СОМ интерфейсы значат больше, чем реализующие их компоненты

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

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

Другие преимущества интерфейсов СОМ

Сценарий, написанный в начале этой главы, иллюстрирует две причины, по которым стоит использовать интерфейсы. Во-первых, они позволяют Вам подсоединить космический корабль к «Фольксвагену». Нет, шутки в сторону… Во-первых, интерфейсы предохраняют систему от повреждений при модификации. До тех пор, пока применяются одни и те же стыковочные узлы, и космический корабль, и орбитальная станция могут изменяться. Во-вторых, интерфейсы позволяют клиенту работать с разными компонентами единообразно. Эта способность к унифицированной работе с разными компонентами известна как полиморфизм (polymorphism). Космический «челнок» работает с каждым объектом, имеющим стыковочный узел, так, будто это орбитальная станция. Ниже мы обсудим полиморфизм подробнее.

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

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

Реализация интерфейса СОМ

Теперь рассмотрим код, реализующий простой интерфейс. В приведенном ниже тексте программы компонент CA использует IX и IY для реализации двух интерфейсов.

class IX

// Первый интерфейс

{

 

public:

 

virtual void Fx1() = 0;

 

virtual void Fx2() = 0;

 

};

 

class IY

// Второй интерфейс

{

 

Соседние файлы в предмете Программирование на C++