三个月就学成这样,我必须要佩服你的。想当初,光面向对象就耗了我不知多少时间,唉~~>>--------------------------------------------------------------------------首先是说明一些万变不离的东西:    接口仍然是一种面向对象的产物,所以在设计程序是也需要使用面向对象的设计思路,不能还是像过去的结构化设计那样,引用起来一片乱麻。    应该考虑到封装,就是将接口的调用、生命周期封状在你的某个对象内部(当然,这个对象也可以是TForm、TApplication),但一个更好的做法则是,将该对象的所有的功能使用进行组合,重新构造一个新的功能封装的对象,而不是到处的创建、转换。(有一个例外,就是可用于操作系统全局进程的自动化对象,如:“Word.Application”,可以不销毁该对象而由其它进程去控制,但这中情况下最好使用Variant类型及IsEmpty函数等进行自动控制,虽然慢一点;否则一定要亲自释放。)    封装时应当注意的就是对接口的生命周期的控制,譬如:方法一:仅在对象的Create事件中创建一次(实现接口的对象)并传递给接口指针(而不论你是用哪种引用方式),且仅在对象的Destory事件里销毁对象(实际上只是将其置为nil即可销毁);方法二,在构造函数和析构函数(就是上面两个)中不做处理,而是在每次调用时都重新创建和释放。(如果按照这些基本准则去做,那么也不会有你那样的问题了)>>-------------------------------------------------------------------------下面简单回答你的问题:(问题1)procedure 1
begin
  MyIntf := MyObj as IMyInterface;
  other statements;
end;    看接口引用计数的规则第五条或是第六条。将接口传递给接口或是不确定情况,将可能导致智能指针的一次递减计数,所以需要超前进行_AddRef引用。    我说这条语句早已不仅仅是简单的类型检查和赋值了,就像C++中的重载操作符一样(Delphi中许多情况下都隐含编译了操作符重载),它在编译后将不是一个简单操作符的能,而是编译为一段相关的处理函数。这段函数的设计原理是什么?没有人知道。    你需要我强差人意的所谓“完全解释”么?你要,我也不会给!    我所能说明的是:这条语句的意义可以理解成将原来的全局接口的智能指针传重新递给自己。“可能”导致中间会有一次递减计数,而当你强行增加计数后,对象就不会被轻易销毁了。你说呢?>>-------------------------------------------------------------------------(问题2)procedure 2
begin
  MyIntf := MyObj;
  other statements;
end;不用说,这是一个标准的传递,中间将产生一个新的智能指针(原来哪个也应当自动销毁了)。应该没有什么可以非议的地方了>>-------------------------------------------------------------------------(问题3)procedure 3
begin
  DoSomething(MyObj as IMyInterface);
  other statements;
end;    关于这样的代码……?我没有做过类似的事情,也不愿意去实验,更不想去强行理解。这里要注释的:与上次有一点不同,就是,这不是接口传递给接口,所以不能直接套用我上次对用as传递接口的解释。    我的程序里不会有这样的代码,就像我编的C程序里面也不可能出现“i+++++++j”或“i--------j”一样。我会将每个“++”、“--”按部就班的写出来。这里我也会按部就班的创建对象,引用接口指针……(不要在Delphi中这样做,他会使你的程序比落地的玻璃杯还要脆弱)>>--------------------------------------------------------------------------注:    我不可能准确地告诉你Delphi的编译器是如何做的。因为Borland都将其隐含了,他们的目的就是不想让你知道,而导致你可能去做许多无谓的事情。且从未见到过Borland对其编译器原理作类似的阐述。所以最多也仅仅是我自己的理解方式,否则你只有自己去问Borland的编译器设计工程师了。    要是哪天Borland公布它的编译器原理,我倒很乐意看看。而现在,去追根刨底那些(本来存在着标准答案,而又不可能得到标准答案)的问题,对于我来说是大没有必要的。    若是想多了解一些COM底层代码的细节,你可以去研究C++,确实会增强一些对COM的底层编码的理解,因为C++中都是显式的代码,基本可以和编译代码一一对照。但是可以告诉你,即便你将C++的COM模型研究明白了,你仍然不可能准确地阐述Delphi中COM模型的具体实施,因为你只可能是对它进行--猜测!    需要说明的是:研究明白C++的COM模型后,当你实际的用C++开始设计、构建COM对象时,你“也”不应详细到直接编写它的底层设计代码,其原理也只是帮助理解而已。事实上,你所需要用到的仍然只是其使用的规则。    再退一步,呵呵~~,如果你在编写COM组件时真的修改到了其底层代码,甚至哪怕是用到手工“调度”功能,我相信你的COM模型很可能是不安全的,或者至少说是不通用的,否则的话——
    我也绝不会认为这样的人是天才,他“最多”只是个疯子(疯子有时还懂得节制呢),因为他根本不懂得如何将知识进行堆砌。盖不了房子,永远打地基;不,地基也打不了,只是在不停的砸碎砖头…    再如果,你确实是疯子,哈哈,还有一条路可以走。就是用Delphi的汇编调试器一步一步走。不过,我也同样相信,这是一条不归路……:(    自然,超人更是绝对不会犯傻而做出那样的事情来的……(哪怕是调试CPUID指令,我也会先找到Intel或AMD的EAX参数的值的设置说明,然后再去调试):)    注明:我也不是要你不求甚解。不错,编程有时需要吹毛求疵,那是因为可能有一些关系到程序设计主旨的原因;但Delphi中既然已经将COM进行了严密、智能(且保密)的封装,就是要使其它人能够减轻负担,将精力投入到更高层次的设计开发(这与面向对象的设计初衷是相同的)。    而我仍然用Delphi来编写程序,包括编写COM,不需要理睬那讨厌的“IDL”以及许许多多的繁心事……    最后,还要谢谢你的关心!    我嘛:身体拜棒儿!吃嘛儿嘛香儿!您瞅瞅呵~,Delphi!……¤!众人皆倒!

解决方案 »

  1.   

    阿明:再次谢谢你的解答!你给我的答案已经足够了,有些东西没必要深究,我的目的毕竟是用来开发应用,掌握一点原则就行了。这样以后即使出现了问题,也大概知道问题的所在。这个话题到此结束,十分感谢。我觉得你很有个性,也一定是个很有才气的人。我已经30出头了,以前的工作只能说和电脑有关,和软件差很远。改行学DELPHI我是下了很大决心,但我最关心的是设计方面的工作,所以很多问题只能不求甚解,但一些关键思想还是要把握。以后请不吝指教!