2010-02-23 48 views
2

我有一个ATL COM对象需要公开其他COM对象的集合,因此客户端可以找出集合中有多少个对象(通过我可以提供的一个简单的Count属性)和访问对象使用其索引。这个对象集合是动态的 - 计数不是固定的 - 我不知道当我的主(父)对象被构造时会有多少(因此我不能在我的FinalConstruct中创建这些对象)。我想要公开的对象只有只读属性。COM对象的动态数组

我想要做的是在第一次需要时创建一个std::vector这些对象。我想在可能的情况下使用ATL智能COM指针,因此我不需要手动管理引用计数等,但我不确定是否应该使用CComPtr,'CComQIPtr'等。

假设对象我要回被称为IChild,我希望我可以做这样的事情:

std::vector<CComPtr<IChild> > children; 
... 
CComPtr<IChild> child; 
// Somehow instantiate an IChild? 
... 
children.push_back(child); 

STDMETHODIMP Parent::GetAt(LONG index, IChild** pRet) 
{ 
    *pRet = children[index]; 
} 

如果任何人有我如何能做到这一点的任何指针,我会非常欢迎的。有一个excellent article on exposing a static object,但我无法找到关于特定问题的任何信息。

回答

6

是的,std::vector< CComPtr<IChild> >是做到这一点的方法 - 您将获得一个动态数组IChild*,它管理IChild衍生对象的生存期。一旦你想将IChild*转换为派生接口,你将不得不使用QueryInterface(),就像你使用带有C++对象的dynamic_cast一样。

对阵列使用CComQIPtr毫无意义。 CComQIPtr的主要用途是有一个方便的方法来调用QueryInterface()指向可能实现感兴趣接口的对象的指针。不要调用QueryInterface()并检查结果,而是调用CComQIPtr构造函数,并检查结果对象是否包含非空指针。您可以在使用数组的代码中使用CComQIPtr,但将数组用于数组本身没有意义。

+2

实际上,从MSVS2010开始,它必须是'std :: vector >>,因为不幸的操作符和重载:http://blogs.msdn.com/b/vcblog/archive/2009 /05/25/stl-breaking-changes-in-visual-studio-2010-beta-1.aspx – mcmcc 2013-03-05 16:49:50

+0

尽管在C++ 11中不需要CAdapt:http://stackoverflow.com/questions/24285016/ do-vectors-of-ccomptr-still-need-cadapt – 2014-06-18 16:03:08

+0

使用ATL :: CComObject的'std :: vector'也可以吗? – 2015-09-10 13:00:11

2

CComPtr<...>假设您为其分配了兼容接口。 CComQIPtr<...>调用IUnknown::QueryInterface以获得正确的界面。这就是为什么它需要额外的GUID作为模板参数。

出于您的目的,您应该使用CComPtr,因为您知道您将始终使用IChild初始化条目。