В программировании интерфейс IUnknown является фундаментальным интерфейсом в Component Object Model (COM). Спецификация COM [1] предписывает, что объекты COM должны реализовывать этот интерфейс. Более того, любой другой интерфейс COM должен быть производным от IUnknown. IUnknown предоставляет две основные функции всех объектов COM: управление жизненным циклом объекта посредством подсчета ссылок и доступ к функциональности объекта через другие интерфейсы .
Интерфейс IUnknown (или IUnknown-derived) состоит из указателя на таблицу виртуальных методов , которая содержит список указателей на функции, реализующие функции, объявленные в интерфейсе, в том порядке, в котором они объявлены в интерфейсе. Накладные расходы на внутрипроцессный вызов, таким образом, идентичны вызовам виртуальных методов в C++. [2]
Интерфейс IUnknown предоставляет три метода : QueryInterface
, AddRef
, и Release
: [3]
QueryInterface
позволяет вызывающему объекту извлекать ссылки на интерфейсы, которые реализует компонент. Это похоже на dynamic_cast<>
в C++ или приведения в Java и C# . В частности, это используется для получения указателя на другой интерфейс, заданного GUID , который уникально идентифицирует этот интерфейс (обычно называемый идентификатором интерфейса или IID ). Если объект COM не реализует этот интерфейс, вместо этого возвращается ошибка E_NOINTERFACE.AddRef
используется для увеличения счетчика ссылок, когда новый клиент получает объект. Возвращает новый счетчик ссылок.Release
используется для уменьшения счетчика ссылок, когда клиенты закончили использовать объект. Он возвращает новый счетчик ссылок. Объект удалит себя во время освобождения, когда счетчик ссылок достигнет нуля, что означает, что вызывающий объект никогда не должен использовать интерфейс после вызова Release.интерфейс IUnknown { virtual HRESULT QueryInterface ( REFIID riid , void ** ppvObject ) = 0 ; virtual ULONG AddRef () = 0 ; virtual ULONG Release () = 0 ; };
Идентификатор интерфейса IUnknown определяется как GUID со значением {00000000-0000-0000-C000-0000000000046}.
Интерфейсы компонента COM должны обладать рефлексивными, симметричными и транзитивными свойствами. Рефлексивное свойство относится к способности вызова QueryInterface
заданного интерфейса с идентификатором интерфейса возвращать тот же экземпляр интерфейса. Симметричное свойство требует, чтобы при извлечении интерфейса B из интерфейса A через интерфейс A QueryInterface
также был доступен для извлечения из интерфейса B. Транзитивное свойство требует, чтобы если интерфейс B доступен из интерфейса A, а интерфейс C доступен из интерфейса B, то интерфейс C должен быть доступен для извлечения из интерфейса A.