前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >重温Delphi之:面向对象

重温Delphi之:面向对象

作者头像
菩提树下的杨过
发布2018-01-23 14:44:27
7220
发布2018-01-23 14:44:27
举报
文章被收录于专栏:菩提树下的杨过

任何一门语言,只要具备了"封装,继承,多态"这三项基本能力,不管其实现方式是直接或曲折、复杂或简洁,就可以称之为“面向对象”的语言。

Delphi当年的迅速走红,是以其RAD快速开发吸引程序员的目光。这无疑是它最吸引人的优势,但同时也让人误以为delphi只是vb的高级版本,从而忽视了其面向对象的特性。

其实Pacscal发展到Delphi,已经完全具备了面向对象的所有特点:允许自定义类,类可以继承(单继承),允许方法重载/覆写,可以定义接口,类可以实现接口,允许定义静态方法(即class方法),虚方法,抽象类...等等,对于delphi怀有偏见的朋友,你还会怀疑delphi的面向对象能力吗?

下面是一些演示代码: 1.先定义一个基类TPeople

代码语言:js
复制
unit UPeople;

interface

type
  TPeople = class(TObject)
 
 private
    _name:string; //私成成员定义
 procedure Set_Name(value:string);//Name属性的set方法定义
 function Get_Name:string; //Name属性的get方法定义

 protected
 function Get_Sex:Boolean;virtual;abstract; //定义抽象虚方法,由子类去实现
 
 public
 property Name:string read Get_Name write Set_Name; //定义Name属性
 property Sex:Boolean read Get_Sex; //定义Sex只读属性(该属性并未实现,而是交由子类去实现)
 class function ToString:string; //类方法,有点象c#中的static静态方法 
 procedure ShowName;//公用实例方法    
end;

//实现部分
implementation

 procedure TPeople.Set_Name(value:string);
 begin
      _name := value;
 end;

 function TPeople.Get_Name:string;
 begin
      result := _name;
 end;

 class function TPeople.ToString:string;
 begin
      result := 'This is a People Class';
 end;

 procedure TPeople.ShowName;
 begin
      Writeln('姓名:' + _name);
 end;    
end.

2.再定义一个子类TMan

代码语言:js
复制
unit UMan;
 
interface

uses
     UPeople ;
 
type
  TMan = class(TPeople)

 constructor Create(name:string); overload ; //重载构造函数

 
 private
    _sex:Boolean;

 protected
 function Get_Sex:Boolean; override;


 public
 function ToString:string; //实例方法

 end;

implementation

 constructor TMan.Create(name:string); //注意写法:实现的时候不用加overload关键字
 begin
 inherited Create;
     _sex := true; //男性强制定义为true
     Self.Name := name;
 
 end;

 function TMan.Get_Sex:Boolean;
 begin
    result := _sex;
 end;

 function TMan.ToString:string;
 begin
    result := '这是TMan中的ToString方法';
 end;

 
end.

3.再来一个子类TWoman

代码语言:js
复制
unit UWoman;

interface

uses
     UPeople,UICook;
 
type
  TWoman = class(TPeople,ICook)

 constructor Create(name:string); overload ;

 
 private
    _sex:Boolean;

 protected
 function Get_Sex:Boolean; override;

 public
 procedure Cook;//接口的方法实现定义
 procedure ShowName;overload;

 //如果Class是从TObject继承的,又想实现接口的话,必须实现下面这三个function,
 //如果想偷懒的话,把UPeople改成从TInterfacedObject继承就可以省掉这个步骤了
 function _AddRef:Integer; stdcall;
 function _Release:Integer;stdcall;
 function QueryInterface(const IID:TGUID;out Obj):HResult; stdcall;
 end;

implementation

 function TWoman._AddRef:Integer;
 begin
      result :=-1;
 end;

 function TWoman._Release:Integer;
 begin
      result :=-1;
 end;

 function TWoman.QueryInterface(const IID:TGUID;out Obj):HResult;
 const
      E_NOINTERFACE = $80004002;
 begin
 if   GetInterface(IID,Obj) then
          Result := 0
 else
          Result := -1; {E_NOINTERFACE}
 end;   

 
 constructor TWoman.Create(name:string);
 begin
 inherited Create;
     _sex := false;
     Self.Name := name;     
 end;

 function TWoman.Get_Sex:Boolean;
 begin
    result := _sex;
 end;

 procedure TWoman.ShowName;
 begin
    Writeln('女人总是喜欢搞点花样,所以重载一下哈.')
 end;

 procedure TWoman.Cook;
 begin
    Writeln('因为我实现了ICook接口,所以我会做饭:)')
 end;

end.

注意,TWoman这个子类实现了接口ICook,其定义如下:

4.ICook接口

代码语言:js
复制
unit UICook;

interface

type
  ICook = interface //定义一个接口
 procedure Cook;//接口的方法定义 
 end;

implementation

end.

5.放到ConsoleApplication中测试一把:

代码语言:js
复制
program ClassDemo;

{$APPTYPE CONSOLE}

uses
  SysUtils,
  UPeople in 'UPeople.pas',
  UMan in 'UMan.pas',
  UWoman in 'UWoman.pas',
  UICook in 'UICook.pas';

var
  aPeople:TPeople;
  aMan:TMan;
  aWoman:TWoman;
  aCook:ICook;

begin
  aPeople := TPeople.Create;
  aPeople.Name := 'jimmy.yang';
  Writeln(aPeople.Name);
  Writeln(TPeople.ToString);//调用静态方法
  aPeople.ShowName;

  Writeln('----------------------------------------');
 
  aMan := TMan.Create('杨俊明');
  Writeln(aMan.Name);
  Writeln(aMan.Sex);
  aMan.ShowName; //通过继承得来的方法
  Writeln(aMan.ToString);//TMan实例中的对象方法

  Writeln('----------------------------------------');

  aWoman := TWoman.Create('小龙女');
  Writeln(aWoman.Name);
  Writeln(aWoman.Sex);
  aWoman.ShowName; //调用重载后的方法
  aWoman.Cook;//实现接口得来的方法   
  Writeln('----------------------------------------');
  aCook := ICook(aWoman);//类还可以转化为接口
  aPeople.Free;
  aPeople:= TWoman.Create('翠花'); //同样也允许子类创建得到父类
  aPeople.ShowName;
  aWoman.Free;
  aWoman := TWoman(aPeople);
  aWoman.Cook;
  Readln;
end.

运行结果: jimmy.yang This is a People Class 姓名:jimmy.yang ---------------------------------------- 杨俊明 TRUE 姓名:杨俊明 这是TMan中的ToString方法 ---------------------------------------- 小龙女 FALSE 女人总是喜欢搞点花样,所以重载一下哈. 因为我实现了ICook接口,所以我会做饭:) ---------------------------------------- 姓名:翠花 因为我实现了ICook接口,所以我会做饭:)

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2009-12-15 ,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档