dcba:
你这个问题涉及很多方面啊!
好,我就耐心地说说自己的看法。
C++Builder共享Delphi的VCL(VCL是用Object Pascal写的),这是由于这一点,很多人都瞧不起
它,认为它不是纯粹意义上的C++,是个大杂烩。其实,Delphi也不是完全用Object Pascal写
的。Delphi编译的程序执行效率(听好,我说的是执行效率,不是开发效率)这么高,说白了就是
运行速度这么快,是有原因的。原因就是Delphi和C++Builder都共享了Borland C++的编译器
的后端,所以,它们三个编译出的目标文件的格式是一致的,所以,运行效率也理所当然地很
相近。我说这话是有根据的,以前在某本书上看到过,现在一时想不起来了 :-( 好在,还可以
找到另一个证据,在http://www.delphibbs.com/delphibbs/dispq.asp?lid=62610这个帖子中,
aimingoo大侠的分析是最好的佐证。所以,我一直以来对C++Builder的看法还是很不错的!
言归正传,
其实,如果你细心一点的话,应该能发现,在你的工程中,将xxx.pas文件删除掉,将编译好的
xxx.obj加入进工程,一样能够编译通过。其实拓展开去,C++Builder使用的库文件是.lib,
(.lib可以看作是许多个.obj文件链接成的),这就是为什么在C++Builder中只写上#include <vcl.h>
或#include "xxx.hpp"就可以了,而没有加入.pas或.obj,就是因为都已经在.lib文件中了,
直接链接就可以了。
如果不信,你可以试一试,你将../Borland/CBuilder5/Source/Vcl下的*.pas全部删除或移到
搜索路径找不到的地方,你建立一个功程,编译运行一下,没有丝毫影响。进一步,你再将
../Borland/CBuilder5/Lib/Obj下的*.obj都删除,也没事。但*.hpp和*.lib文件删除可就
不行咯。
那么,怎样才能是改动的VCL代码生效呢?这一点BCB确实要比Delphi麻烦一些,拿修改标准
对话框显示信息的consts.pas为例:
1. 新建一工程,将汉化后的consts.pas拷贝到这个工程所在的目录下,加入工程中,也就是View-->
Project Manager-->选中该工程-->在右键弹出菜单中选择Add,将consts.pas加入进去,保存。
2. Project-->Options,在Compiler页中单击Release按钮,这是为了去掉编译后的目标代码中的调试
信息,然后,编译此工程。
3. 将../CBuilder5/Lib/Release/Vcl50.lib复制到工程所在的目录中,在命令行下执行
tlib Vcl50.lib -+consts.obj,然后将新的Vcl50.lib再复制回去,至此大功告成。
4. 你可以另新建一工程来试一下,不过,由于我们刚才修改的是../CBuilder5/Lib/Release/Vcl50.lib,
所以要静态编译才行,其实,还有一个Vcl50.lib,那就是../CBuilder5/Lib/Debug/Vcl50.lib,它们
之间的区别我就不多说了。
以上的修改过程进一步证明了C++Builder使用的库文件是.lib文件。
至此,问题解释清楚了。
>>小笨苯:
>>你说可以那我该怎样写pas的dll,在里面声明类?在c++builder该怎样调用这个dll的类呢?
哎呀!是哪个家伙节外生枝,说什么在dll中声明类,和这个题目有什么关系?
好,为什么说明“可以”,我就从书上抄一段代码吧。5~~~~我以后再也不多嘴了
嘿嘿
==================================================================================
为了能使用DLL中的类及其成员,必须在DLL中专门输出一些例程作为类及其成员的外壳,外部
程序调用的仍然是这些输出的例程,而这些例程专门操作于类及其成员,从而达到在外部访问
DLL中类和其成员的目的。
{ DLL工程文件 }
Library MyDLL;
uses
Unit1 in 'Unit1.pas';
Unit2 in 'Unit2.pas';
end.
{ Unit1单元文件 }
Unit Unit1;
Interface
type { 声明一个类 }
TMyClass = Class
private
Numbar: Integer;
protected
Procedure HowToAdd(I: Integer);
virtual;
{ 加法操作 }
public
constructor Create(InitalValue: Integer);
Property Add: Integer read Number write HowToAdd;
end;
var
MyClass: TMyClass;
Implementation
constructor TMyClass.Create(InitialValue: Integer);
begin
Number := InitialValue;
end;
procedure TMyClass.HowToAdd(I: Integer);
begin
Number := Number + I;
end;
{ Unit2单元文件 }
Unit Unit2;
Interface
uses
Unit1;
{外壳函数}
function CreateMyClass(InitialValue: Integer):TMyClass;
stdcall;
{ 构造 }
procedure FreeMyClass(MyInstance: TMyClass);
stdcall;
{ 析构 }
function MyAdd(MyInstance: TMyClass;
I: Integer):Integer;
stdcall;
exports
CreateMyClass, FreeMyClass, MyAdd;
Implementation
function CreateMyClass(InitialValue: Integer): TMyclass;
begin
Result := TMyClass.Create(InitialValue);
end;
procedure FreeMyClass(Myinstance: TMyClass);
begin
MyInstance.Free;
end;
function MyAdd(MyInstance: TMyClass;
I: Integer):Integer;
begin
MyInstance.Add := I;
Result := MyInstance.Add;
end;
==================================================================================