COM学习笔记1_COM初步探索
来源:互联网 发布:淘宝购物返利那个高 编辑:程序博客网 时间:2024/04/30 07:32
COM组件的两个重要需求:
1。 动态链接
2。 隐藏实现细节
COM初步探索
一个典型C++客户和组件的例子
在COM中,推荐使用接口的指针来使用组件,上面客户端可以改成如下工作:
接下来问题是:
1。 CA* pA = new CA ;
这里暴露太多细节,最起码客户需要类CA的头文件声明,这里把类CA的内部细节(私有成员)都暴露了,
而且当CA的实现细节改动,客户端肯定需要重新编译代码。
另外COM组件可能不在客户进程中,甚至在远程机器上,这样就不可能简单new出组件实例。
2。delete pA ;
这里需要显示释放组件。
但pIX和pIY也指向pA的对象,delete pA后如果再使用pIX等就会发生错误。
容易造成代码维护困难。
解决方案是所有接口派生自IUnknown。
IUnknown提供QueryInterface,AddRef和Release接口。
另外提供函数CreateInstance。
对于上面问题1,通过CreateInstance创建组件,并返回IUnknown接口指针,
然后通过QueryInterface再获取各种接口的指针。
对于上面问题2,每次获取组件指针时(自动)调用AddRef,该指针不再使用时调用Release。
组件内部维护引用计数,当计数为0时自动释放自己。这样就不需要手动new和delete了。
现在组件和客户代码如下:
1。 动态链接
2。 隐藏实现细节
COM初步探索
一个典型C++客户和组件的例子
- // 组件模块
- interface IX
- {
- virtual void __stdcall Fx1() = 0 ;
- virtual void __stdcall Fx2() = 0 ;
- } ;
- interface IY
- {
- virtual void __stdcall Fy1() = 0 ;
- virtual void __stdcall Fy2() = 0 ;
- } ;
- // Interface implementation
- class CA : public IX,
- public IY
- {
- //......
- } ;
- // 客户模块
- int main()
- {
- CA* pA = new CA ;
- pA->Fx1() ;
- pA->Fx2() ;
- pA->Fy1() ;
- pA->Fy2() ;
- delete pA ;
- }
在COM中,推荐使用接口的指针来使用组件,上面客户端可以改成如下工作:
- // 客户模块
- int main()
- {
- CA* pA = new CA ;
- // Get an IX pointer.
- IX* pIX = pA ;
- pIX->Fx1() ;
- pIX->Fx2() ;
- // Get an IY pointer.
- IY* pIY = pA ;
- pIY->Fy1() ;
- pIY->Fy2() ;
- delete pA ;
- }
接下来问题是:
1。 CA* pA = new CA ;
这里暴露太多细节,最起码客户需要类CA的头文件声明,这里把类CA的内部细节(私有成员)都暴露了,
而且当CA的实现细节改动,客户端肯定需要重新编译代码。
另外COM组件可能不在客户进程中,甚至在远程机器上,这样就不可能简单new出组件实例。
2。delete pA ;
这里需要显示释放组件。
但pIX和pIY也指向pA的对象,delete pA后如果再使用pIX等就会发生错误。
容易造成代码维护困难。
解决方案是所有接口派生自IUnknown。
IUnknown提供QueryInterface,AddRef和Release接口。
另外提供函数CreateInstance。
对于上面问题1,通过CreateInstance创建组件,并返回IUnknown接口指针,
然后通过QueryInterface再获取各种接口的指针。
对于上面问题2,每次获取组件指针时(自动)调用AddRef,该指针不再使用时调用Release。
组件内部维护引用计数,当计数为0时自动释放自己。这样就不需要手动new和delete了。
现在组件和客户代码如下:
- // 组件代码
- interface IX : IUnknown
- {
- virtual void __stdcall Fx() = 0 ;
- } ;
- interface IY : IUnknown
- {
- virtual void __stdcall Fy() = 0 ;
- } ;
- // Forward references for GUIDs
- extern const IID IID_IX ;
- extern const IID IID_IY ;
- class CA : public IX,
- public IY
- {
- virtual HRESULT __stdcall QueryInterface(const IID& iid, void** ppv) ;
- virtual ULONG __stdcall AddRef() { return 0 ;}
- virtual ULONG __stdcall Release() { return 0 ;}
- virtual void __stdcall Fx() { cout << "Fx" << endl ;}
- virtual void __stdcall Fy() { cout << "Fy" << endl ;}
- } ;
- IUnknown* CreateInstance()
- {
- IUnknown* pI = static_cast<IX*>(new CA) ;
- pI->AddRef() ;
- return pI ;
- }
- // 客户代码
- int main()
- {
- IUnknown* pIUnknown = CreateInstance() ;
- IX* pIX = NULL ;
- if (SUCCEEDED (pIUnknown->QueryInterface(IID_IX, (void**)&pIX)))
- {
- pIX->Fx() ; // Use interface IX.
- }
- IY* pIY = NULL ;
- if (SUCCEEDED (pIUnknown->QueryInterface(IID_IY, (void**)&pIY)))
- {
- pIY->Fy() ; // Use interface IY.
- pIY->Release() ;
- }
- IY* pIYfromIX = NULL ;
- if (SUCCEEDED (pIX->QueryInterface(IID_IY, (void**)&pIYfromIX)))
- {
- pIYfromIX->Fy() ;
- pIYfromIX->Release() ;
- }
- pIX->Release() ;
- pIUnknown->Release() ;
- }
0 0
- COM学习笔记1_COM初步探索
- COM学习笔记1_COM初步探索
- COM学习笔记1_COM初步探索
- COM学习笔记2_COM接口vbtl内存布局
- COM学习笔记2_COM接口vbtl内存布局
- COM学习笔记2_COM接口vbtl内存布局
- COM学习笔记6_COM的复用:包容和聚合
- iOS学习笔记: 初步探索KVC & KVO
- COM组件运作机制的初步探索
- Fcm算法初步学习探索
- COM学习笔记1
- 【学习笔记】汇编初步1
- Android开发艺术探索学习笔记 1
- Win8探索学习笔记
- COM 学习笔记(1)
- COM 学习笔记(1)
- Html学习笔记(1)-Html初步
- html+css初步学习笔记(1)
- centos6.x下让redis以服务方式运行
- 黑马程序员——java概述
- 4Sum
- 欢迎使用CSDN-markdown编辑器
- Oracle数据库之创建表空间与用户
- COM学习笔记1_COM初步探索
- transient关键字
- 单链表
- java 线程中 stop()和 suspend()方法为何不推荐使用?
- 在win7(32)以及xp上python环境的搭建
- 项目管理 01
- uchome各个功能模块对应模块说明
- 黑马程序员---集合-Map集合,Collections类
- 生产订单修改记录