韩小明@xiammy的专栏

没水的地方挖井,有水的地方修渠

韩小明ID:xiammy
439161次访问,排名106好友12人,关注者67
毕业后一直在广联达工作
xiammy的文章
原创 174 篇
翻译 0 篇
转载 22 篇
评论 1133 篇
韩小明的公告
作者毕业于浙江大学,非常热爱体育运动。现在尤其热爱羽毛球运动。在休息时间非常热爱技术文章写作。
最近垃圾评论泛滥,为了不污染大家的视听,暂时关闭评论,请大家理解。
欢迎转载,但请注意,除非特别声明,本站采用Creative Commons License许可:署名,非商业。

最近评论
yb00k:感觉 这个还是个垃圾东西 适合IE7的变到IE8 就变样了 点都不规范 一点兼容性都不强....强烈支持 firefox
wuhuiran:我嵌入式数据库一直用BerkeleyDB,看到你的博文才知道还有一个SQLite,谢谢。BerkeleyDB不支持SQL
wuhuiran:我嵌入式数据库一直用BerkeleyDB,看到你的博文才知道还有一个SQLite,谢谢。BerkeleyDB不支持SQL
liquankun:瑞星还是不咋地!
白花了几个月的钱
外国的杀软不一定比国产的好!
但是国产的就是比不上国外的!
没办法!技术赶不上人家 还竟搞内讧
不经历大灾难 就不知道什么是团结!



正真的高手是不用杀毒软件的,没什么好不好的,是你自己技术不行而已
wangdei:http://www.bt285.cn BT下载 有300W部BT种子.
http://www.yaonba.com.cn NBA中文网 有200W条NBA直播
http://www.5a520.cn 小说520网 有300W部小说
http://www.bt285.cn/yazhou/ 亚洲BT 有BT亚洲
http://www.bjxlz.cn p……
文章分类
收藏
    相册
    图书
    链接
    宗刚的专栏(RSS)
    快乐学习(RSS)
    陈亮亮的专栏(RSS)
    朋友
    张恂论 OO
    言之有李(RSS)
    赵伟的小家
    存档
    订阅我的博客
    XML聚合  FeedSky

    原创 苛评VCL: 孤独的Application收藏

    新一篇: 苛评VCL: 穿不透的类型 | 旧一篇: 苛评VCL: 臃肿的Windows控件

    由于每次都可能有人是单独阅读这个系列的文章。我想重申一下我的苛评VCL的意义。不在于说VCL的不好,而是重点将发现到一些问题暴露出来,以此来说明我认为VCL原来处理不合适的地方。这永远是一个设计问题,而不是技巧问题。中间难免有争议。不过请大家将争议的目标锁定在设计本身。毕竟,针对特定情况的争议才是有意义的。

    说起Application,稍微知道Delphi的人都知道。我们最常使用的Application的几个方法是:

    • Application.CreateForm
    • Application.ProcessMessage
    • Application.MainForm
    • ...

    这些方法带领我们逐渐去认识Application。事实上,Delphi中并不止一个Application。我们平常见到最多的是Forms单元中定义的TApplication。如果你创建一个控制面板应用的话,会发现在CtlPanel单元中定义了一个TAppletApplication。但是它在dpr中的使用方法和Application一样。同样,如果你创建一个服务应用的话,会在SvcMgr单元中,发现另一个Application,叫TServiceApplication。这些Application都是从TComponent派生出来的,但是之间并没有任何关系,也没有公共的接口。但是都同样有三个办法:Initialize,CreateForm,Run。此乃Application的第一孤独,虽有众多兄弟,但是却只能有一个人出现。

    今天我们重点说Forms单元中的TApplication。在李维先生的《Inside VCL》中对这个类的功能做了非常详细的解释。其主要作用是创建了一个隐藏的窗体,来统一处理消息循环,以此简化TForm的设计。另外你如果了解以上几个另类的Application,就会发现,你可以非常简单的将自己的Form移植到其他类型的应用中,而不需要修改太多的代码。

    可是,我们在说的时候,前提都是Application在一个Exe程序中的。如果我们将它放到Dll中呢?因为Application是定义在Forms单元中,可以想像,如果我们在Dll中使用了窗体。Exe和Dll之间将会出现两个Application,而且这两个Application是不一样的。最典型的现象就是如果在Dll中直接ShowModal一个窗体,它和MainForm不会共享一个任务栏Button。解决过这个问题的人都知道,这个原因在于Handle不一样。

    但这不是在讨论如何解决不一样的技巧,事实上我们在实际编程中,都会采用很多方式来规避这个问题。可是,如果我们将这个问题提升到设计领域,那么几乎可以认为,Application并没有处理好Exe和Dll之间的共享问题。

    有一个很奇怪的现象,不知道大家注意到了没有。Application的类型是声明在Forms单元中的,但是创建代码却是在Controls单元中调用的。通过看创建代码,可以看出,Application中模式上讲,应该接近于单例模式。而且是直接创建的。只要你使用Controls单元,Application对象就会被创建起来。这个直接决定了Application的第二孤独,天生没有同伴。除了Application,还有几个相同遭遇的难兄难弟:Screen/Mouse。只要有窗体,Dll中的Application不可避免地被创建出来,而且是不可替换的。

    我认为这个应该是设计上的遗漏。当然了,最好的情况,是约定在Dll中不要使用窗体了!不过这个约定并不是每个人都知道,而且Delphi也没有禁止在Dll中使用窗体。而且从实现上讲,FastMM4,这个和Application同样是类单例模式的内存管理器,就非常好地实现了Exe和Dll之间的共享。

    Application是强大的,强大到你完全不需要关心它。我想这个正是VCL设计它的初衷。可是,当这位英雄遇到一堆英雄的时候,却发现,他们之间是互相独立的。协同不好的英雄除了发挥原有的作用外,也付出了不协调的代价。这正是Application的第三孤独,大家明明就是一个人,却总是不能合体。

    从我们实践的角度,其实就是几个关键值的共享,因此从架构上无需多说什么。但是既然是设计,就必须比应用多考虑到一点,就是Application的版本问题。因为在Exe和Dll之中的Application可能并不是一个版本的Delphi编译出来的,可能是Delphi5/7/2005等等。考虑好版本共享,才能保证以后的运行稳定。

    还是那句话,评VCL是为了更好地理解VCL。 

    发表于 @ 2007年02月07日 07:37:00|评论(loading...)|编辑

    新一篇: 苛评VCL: 穿不透的类型 | 旧一篇: 苛评VCL: 臃肿的Windows控件

    评论

    #zwjchina 发表于2007-02-07 15:07:17  IP:
    请继续!^_^

    楼主发的几篇都读了,有点意思。
    可能有些地方值得再细细推敲。但是,楼主思考问题的方式对我
    是有很大启发的。或者楼主可以尝试与CodeGear联系下,交流
    下看法。
    #lsuper 发表于2007-02-07 18:19:27  IP:
    估计设计时只想着自己的 bpl 了。
    =^0^=
    #lichaohui 发表于2007-02-07 20:29:17  IP:
    不知所云,乱七八糟,
    MFC 中的类似东西也都差不错,倒是英雄所见略同。

    C#.NET 中也有很多单例对象,
    对象全局管理者,通常都是单例的,
    他们都要先于被管理的对象存在。
    #UMU 发表于2007-02-07 20:40:13  IP:
    SDK 天下无敌
    #oury 发表于2007-02-08 02:03:42  IP: 221.233.7.*
    没看明白
    #wr960204 发表于2007-02-08 09:12:02  IP: 61.235.75.*
    呵呵,DLL也不一定会会出现多个Application。
    如果你的EXE和DLL都是带运行时包的话,EXE和DLL是共享一个Application的。DLL中窗体不会和EXE中的有任何区别。
    #MEFULEU 发表于2007-02-08 16:49:56  IP:
    晕死,DLL中可以指定Application嘛,把主程序的句柄传递给他不就可以避免任务栏上出现多余的冬冬了~
    #callzjy 发表于2007-02-09 00:40:18  IP: 61.153.60.*
    晕死,DLL中可以指定Application嘛
    #Rural_Boy 发表于2007-05-16 11:31:20  IP: 125.92.162.*
    真是无聊,一个不脚踏实地的家伙在这里胡言乱语.

    在 dll 中制定 application.handle := 调用程序的 Application.handle

    就可以避免出现两个任务栏.

    如此简单的东西都不明白,回家睡觉去吧.再玷污 VCL 就找 Borland 告你.
    #hero_yin 发表于2007-11-13 09:53:03  IP: 219.133.7.*
    application.handle := 调用程序的 Application.handle
    只能解决部分问题,实际上application还是存在两份,改成runtime带上vcl的bpl 的话就比较完美了
    楼上的态度有问题,楼主的观点我比较赞成,我开发过DLL带窗口的项目,深受其害
    发表评论  


    当前用户设置只有注册用户才能发表评论。如果你没有登录,请点击登录
    Csdn Blog version 3.1a
    Copyright © 韩小明