3.4:再看看值传递:拷贝构造函数如下
template<> _com_ptr_t(const _com_ptr_t& cp) throw() : m_pInterface(cp.m_pInterface) { _AddRef(); } |
嗯,也不会有问题。
3.5:最后我们也总结一下使用COM智能指针时的注意事项:
·不要在Com智能指针的生命期如果在::CoUninitailize之后,那请在调用::CoUninitailize之前,强制调用MyComPtr = NULL;达到强制释放的目的。否则会出错。
·不要混用智能指针和普通Dispatch指针,不要调用MyComPtr->Release(),这违背智能指针的原意,会在析构时报错。
4:使用ATL提供智能指针:CComPtr或是CComQIPtr.
如果不使用MFC框架,要自已包装IDispatch,生成智能指针,还可以使用ATL提供的智能指针。查看源码,并参照《深入解析ATL》一书,发现实现与_com_ptr_t大同小异,效果一致。
二:引申一下,我们来看看C++的智能指针
1:说到智能指针,我们一定要看看标准C++提供的auto_ptr。而auto_ptr的使用是有很多限制的,我们一条一条来细数:
1.1:auto_ptr要求一个对象只能有一个拥有者,严禁一物二主。
比如以下用法是错误的。
classA *pA = new classA; auto_ptr<classA> ptr1(pA); auto_ptr<classA> ptr2(pA); |
1.2:auto_ptr是不能以传值方式进行传递的。
因为所有权的转移,会导致传入的智能指针失去对指针的所有权。如果要传递,可以采用引用方式,利用const引用方式还可以避免程序内其它方式的所有权的转移。就其所有权转移的做法:可以查看auto_ptr的拷贝构造和=操作符的源码,此处略。
1.3:其它注意事项:
·不支持数组。
·注意其Release语意,它没有引用计数,与com提供的智能指针不同。Release是指释放出指针,即交出指针的所有权。
·auto_ptr在拷贝构造和=操作符时的特珠含义决定它不能做为STL标准容器的成员,
好了,看了上面的注意事项,特别是第三条,基本上可以得出结论:在实际应用场合,auto_ptr基本没什么应用价值的。
2:如何得到支持容器的智能指针。
我们利用auto_ptr的原型,制作一个引用计数的智能指针,则时让它支持STL容器的标准。实现代码很简单,参照了《C++标准程序库》中的代码,关键代码如下:
template<class T> class CountedPtr { T * ptr; long * counter; public: //构造 explicit CountedPtr(T* p = NULL) :ptr(p),count(new long(1){} //析构 ~CountedPtr() {Release();} //拷贝构造 CountedPtr(cont CountedPtr<T>& p) :ptr(p.ptr),count(p.count) {++*counter;} //=操作符 CountedPtr<T>& operator= (const CountedPtr<T>& p) { if(this!=&p) { Release(); ptr=p.ptr; counter=p.counter;++*counter; } return *this; } //其它略 .... private: void Release() { if(--*counter == 0) { delete counter; delete ptr; } } } |
好了,这样,当复制智能指针时,原指针与新指针副本都是有效的,这样就可以应用于容器了。现在,通过CountedPtr包装的C++对象,是不是和Java的对象类似了呢,呵呵。只要再加上一些必要的操作符,它就可以作为容器中的共享资源来使用了。 
说明:本教程来源互联网或网友上传或出版商,仅为学习研究或媒体推广,wanshiok.com不保证资料的完整性。
2/2 首页 上一页 1 2 |