王朝网络
分享
 
 
 

使用类方法控制实例的唯一性

王朝delphi·作者佚名  2006-01-31
宽屏版  字体: |||超大  

使用类方法控制实例的唯一性

CST 2005-7-29

文档目的

在面向对象编程中,出于各种原因,有时我们希望控制一个类的实例仅有一个存在于内存中。例如我在编程中遇到一个实际情况,程序的配置数据保存在XML文档中,需要写一个XML配置文件解析类。由于读入的数据可能很庞大,而且在程序每个模块中都用到该解析类的实例,那么如果每次都创建一个实例并重新读入数据,效率就不令人满意了。

类方法

我们可以通过类方法(Class Method)实现实例创建的控制,其实也有许多其他的方法。这里我先介绍“类方法”的实现。

如下是DELPHI对类方法的定义:

A class method is a method (other than a constructor) that operates on classes instead of objects. The definition of a class method must begin with the reserved word class. For example,

type

TFigure = class

public

class function Supports(Operation: string): Boolean; virtual;

class procedure GetInfo(var Info: TFigureInfo); virtual;

...

end;

The defining declaration of a class method must also begin with class. For example,

class procedure TFigure.GetInfo(var Info: TFigureInfo);

begin

...

end;

In the defining declaration of a class method, the identifier Self represents the class where the method is called (which could be a descendant of the class in which it is defined). If the method is called in the class C, then Self is of the type class of C. Thus you cannot use Self to access fields, properties, and normal (object) methods, but you can use it to call constructors and other class methods.

A class method can be called through a class reference or an object reference. When it is called through an object reference, the class of the object becomes the value of Self.

定义一个类方法就是在将一个方法生命在PUBLIC段中,并加上class前缀。这样的方法可以由类直接调用,而不需要先创建类的实例。比如构造函数Create就是一个类方法,我们在创建对象实例的时候这样写:

MyObject:=TmyClass.Create;

此时的Create方法由类TmyClass调用。

实现方法

我们实现的目的就是不以平时的对象访问模式调用对象

Myobject:=TmyClass.Create(self);

Try

With Myobject do begin

//do something

end;

finally

FreeAndNil(Myobject);

End;

而是使用一个类方法GetInstance来间接获取对象实例,这个唯一的对象实例被申明在类的单元文件内(后文回详细说明),在GetInstance函数中判断该实例是否被创建赋值,如果没有,则调用构造函数创建;如果已创建,则直接返回该实例。

这里,我们需要将构造函数Create申明在private段中,仅能由GetInstance判断调用。TmyClass.GetInstance函数返回值为TmyClass类型的变量,如果Tmyclass继承自Tcomponent的话,create方法需要一个Aowner参数,因此我为GetInstance增加一个Aowner参数。

GetInstance类方法的实现不影响类中其他方法的实现,一般我们在调试设计阶段不进行类方法的考虑,而是公开需要测试的对象方法以便于调试。最后要发布类的时候,我们做如下改动:

1. 在类单元文件中,但是在类定义之外申明唯一对象变量。

我的做法是在

implementation

var mySoloObject:TMyClass;

2. 隐藏构造函数

将constructor函数申明在private段中

3. 增加一个GetInstance类方法,定义在Public段中,判断mySoloObject是否被创建。

具体代码如下:

……

//类定义

TConfigReader = class(TComponent)

private

FXMLDoc: TXMLDocument;

constructor Create(AOwner:TComponent); override;

public

FCtrlInfoList:TObjectList;

function OpenXMLFile(const APath:string):boolean;

function ReadCtrlInfoToList: Integer;

class function GetInstance(AOwner:TComponent):TConfigReader;

end;

//唯一对象变量

implementation

var

ConfigReaderSolo:TConfigReader;

//函数定义

class function TConfigReader.GetInstance(AOwner:TComponent):TConfigReader;

begin

if ConfigReaderSolo=nil then

ConfigReaderSolo:=TConfigReader.Create(AOwner);

Result:=ConfigReaderSolo;

end;

访问方法

做了如上修改以后,我们的类就可以实现唯一实例的判断以及创建控制。

在主调单元中,我们想往常一样uses类所在的unit文件,相较普通的对象访问方式,我们采用类似如下的代码:

TConfigReader.GetInstance(Self).MyMethod1;

TConfigReader.GetInstance(Self).MyMethod2;

MyVar:= TConfigReader.GetInstance(Self).MyFunc1;

MyObject:= TConfigReader.GetInstance(Self).Member1;

……

小结

对数据的隐藏、共享、保护是OO编程的优点,利用不同的数据访问级别隐藏相应的方法、成员,可以更大限度控制数据的安全性,也可以让程序按照我们想要的方式运行。类方法和类成员可以在对象没有创建的时候就被访问,因此可以越过对象本身来判断其创建与否。定义在单元内但类外的对象变量可以全局于单元内的所有类。

在我的YAHOO公文包中有这片文章相关的代码,欢迎下载。也希望大家给我提出改进意见。

 
 
 
免责声明:本文为网络用户发布,其观点仅代表作者个人观点,与本站无关,本站仅提供信息存储服务。文中陈述内容未经本站证实,其真实性、完整性、及时性本站不作任何保证或承诺,请读者仅作参考,并请自行核实相关内容。
2023年上半年GDP全球前十五强
 百态   2023-10-24
美众议院议长启动对拜登的弹劾调查
 百态   2023-09-13
上海、济南、武汉等多地出现不明坠落物
 探索   2023-09-06
印度或要将国名改为“巴拉特”
 百态   2023-09-06
男子为女友送行,买票不登机被捕
 百态   2023-08-20
手机地震预警功能怎么开?
 干货   2023-08-06
女子4年卖2套房花700多万做美容:不但没变美脸,面部还出现变形
 百态   2023-08-04
住户一楼被水淹 还冲来8头猪
 百态   2023-07-31
女子体内爬出大量瓜子状活虫
 百态   2023-07-25
地球连续35年收到神秘规律性信号,网友:不要回答!
 探索   2023-07-21
全球镓价格本周大涨27%
 探索   2023-07-09
钱都流向了那些不缺钱的人,苦都留给了能吃苦的人
 探索   2023-07-02
倩女手游刀客魅者强控制(强混乱强眩晕强睡眠)和对应控制抗性的关系
 百态   2020-08-20
美国5月9日最新疫情:美国确诊人数突破131万
 百态   2020-05-09
荷兰政府宣布将集体辞职
 干货   2020-04-30
倩女幽魂手游师徒任务情义春秋猜成语答案逍遥观:鹏程万里
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案神机营:射石饮羽
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案昆仑山:拔刀相助
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案天工阁:鬼斧神工
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案丝路古道:单枪匹马
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:与虎谋皮
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:李代桃僵
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:指鹿为马
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案金陵:小鸟依人
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案金陵:千金买邻
 干货   2019-11-12
 
>>返回首页<<
推荐阅读
 
 
频道精选
 
静静地坐在废墟上,四周的荒凉一望无际,忽然觉得,凄凉也很美
© 2005- 王朝网络 版权所有