dynamic_cast COM-объекта в COM-интерфейс не влияет на счетчик ссылок, не так ли? - PullRequest
2 голосов
/ 22 сентября 2009

Если у меня есть класс C ++, X, который реализует интерфейсы COM IY и IZ, и у меня есть указатель y на интерфейс IY объекта типа X, и я делаю это:

IZ *z = dynamic_cast<IZ *> ( y );

Это не влияет на счетчик ссылок объекта, не так ли? Мне не нужно делать Release (), чтобы учесть это, верно?

Если это имеет значение, я использую ATL / COM.

Я предполагаю, что ответ "нет, это не увеличивает счетчик ссылок, и нет, вам не нужно Release ()", но я хочу убедиться.

Заранее спасибо.

Ответы [ 3 ]

4 голосов
/ 22 сентября 2009

dynamic_cast не должен использоваться по нескольким причинам:

  • Вы не знаете, поддерживает ли пункт назначения RTTI
  • Вы не уверены, что OLE не создает для вас прокси
  • ...

Вместо этого используйте QueryInterface - он будет делать то, что вы хотите.

Даже если вы уверены, что в вопросе выше - приведение не меняет счетчик

3 голосов
/ 22 сентября 2009

Подсчет ссылок для COM-объектов увеличивается, когда кто-то вызывает IUnknown :: AddRef (). QueryInterface (), в соответствии с правилами COM, поскольку он выдает новый указатель интерфейса, внутренне вызывает AddRef ().

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

Несмотря на то, что ATL / MFC делает с мозгом, в этом нет никакой магии. Если вы сомневаетесь, вы всегда можете просмотреть разборку в VS и пройти через нее и доказать себе, что AddRef () не вызывается.

Редактировать: И я хочу повторить то, что сказал Дьюфи, не делайте этого . Используйте QueryInterface (). Или CComQIPtr <> (если вам действительно нужно).

Дальнейшее редактирование: если вы используете CComPtr <> и CComQIPtr <>, вам не нужно вызывать Release (), и большая часть бремени выяснения правильного подсчета ссылок уменьшается. Вы действительно должны подумать об их использовании.

0 голосов
/ 19 августа 2014

В C ++ Builder dynamic_cast на указателе интерфейса COM фактически делает QueryInterface. и возвращенный указатель, если QI завершается успешно, получает AddRef 'd.

Классы, которые реализуют COM-объекты, имеют различные макеты vtable по сравнению с более общими классами C ++, поэтому стиль C ++ dynamic_cast не может работать; поэтому я предполагаю, что именно поэтому C ++ Builder делает более разумную вещь, выполняя QueryInterface.

(Первоначальная идея COM заключалась в том, чтобы обобщить объектную модель C ++, чтобы она не зависела от языка и соответствовала двоичному стандарту; они переименовали dynamic_cast в QueryInterface).

Я полагаю, что верхний ответ относится к MSVC, если dynamic_cast вызывает неопределенное поведение.

...