作者:傅雪莱_ | 来源:互联网 | 2023-05-17 12:22
com的定义是:组件对象模型,主要作用用于分布式环境,可以跨语言,跨平台。要介绍com,就先必须了解接口,为什么可以被其它语言调用,例如java,vb,就是通过接口定义语言
- com的定义是:组件对象模型,主要作用用于分布式环境,可以跨语言,跨平台。
- 要介绍com,就先必须了解接口,为什么可以被其它语言调用,例如java,vb,就是通过接口定义语言idl来实现的,通过midl,将接 口定义翻译成其它语言,然后其它语言就能调用com了。
- 每个组件都有名字,当多个组件启动,为了避免不同组件之间的名字冲突,就用IID来定义组件的接口名,CLSID来定义类名。
- 在接口定义文件idl中,import "unknown.idl",可以引进其它接口文件,被MIDL翻译后,如果是c/c++,就会变成include头文件
- com接口不能从多个接口继承,最终的基接口必须是Iunknown,但是实现类可以继承多个接口。
- 多个接口指向同一个对象,每产生一个接口指针,就调用实现类的addref()。
- com接口中所有的成员函数都是纯虚函数,如果实现类继承了多个接口,则会在类中产生多个虚函数表vtbl,在这些vtbl中有多个相同的函数,比如:addref,release等等,但是在实现类中只需实现一次就行了,编译器会初始化每个vtbl,让它们指向同一个实现函数
- 把类转化为基接口指针事,尽量用static_cast,如果没有相应的接口,会引发编译时错误,比运行时再出错好多了。
不能将实现类指针转化为基接口指针,因为会产生路径二义性,如果需要,则传换成实现类最左边的继承的接口,这样效率更高一点。 eg:class bt:public IA,public IB {}
this---->IA 可以看出转换成IA不需要移动指针,效率较高。
IB
bt
- 在vb和java中,queryinterface()和addref()等等,IUNKNOWN的细节被隐藏在每种语言的虚拟机后面。
eg: java中:ipug pug = (ipug)obj;就会隐式调用queryinterface()。