• procedure of object(一个特殊的指针类型) 转


    理论:     //适用于实现不是某一特定过程或函数
      type 
         TNotifyEvent = procedure(Sender: TObject) of object; 
         首先:procedure也是类型,可以理解为过程类型,定义过程的参数结构,而具体的实现可以动态赋值 
     onclick那样例子: 
         声明:  onclick= procedure(Sender: TObject,a :integer) of object;
         以后你就可以把TNotifyEvent作为过程用了,而不用考虑它实现什么功能,你想onclik  里用户写了什么,都是一样的 ;
            if assign(onclick) then 
              onclick; 
         这样只要TNotifyEvent可以执行,程序就去执行它,控件就是这样实现事件的 
         procedure 指针占4个字节,保存在过程的地址. procedure of object占8个字节,保存过程的地址和类的地址 
         procedure of object 是类过程(类函数),用法如下: 
             1、与普通函数相同点:可以像一般的函数和过程一样在类的实例里作为对象方法调用; 
             2、与普通函数不同点:可以不通过对象,而是通过类来直接调用。 
        也就是说,一般函数和过程必须通过类的实例(对象)来调用,而类过程(类函数)则可以不必通过该类的实例来调用。通过类来调用函数或者过程,可以定义和实现一些不能或者不适合作为某一特定对象行为的方法。 
      应用:
         delphi中经常见到以下两种定义 
         Type 
             TMouseProc = procedure (X,Y:integer);  //一种普通的过程
             TMouseEvent = procedure (X,Y:integer) of Object;//一种对象方法的类型 

          两者样子差不多但实际意义却不一样,两者的区别就在于TMouseEvent类型的方法必须在一个对象里。类方法存在一个隐藏参数self,也就是说两者形参不一样,所以不能相互转换 .
       TMouseProc只是单一的函数指针类型; 
       TMouseEvent是对象的函数指针,也就是对象/类的函数/方法 
     procedure   TForm1.BBB(I:   Integer); 
    begin 
        showmessage( 'BBB: '   +   IntToStr(I)); 
    end; 

    procedure   TForm1.CCC(I:   Integer); 
    begin 
        showmessage( 'CCC: '   +   IntToStr(I)); 
    end; 

    procedure   TForm1.Button1Click(Sender:   TObject); 
        type 
            Taaa   =   procedure   (i:integer)   of   object  
    var 
        ap:   Taaa; 
    begin 
        ap   :=   BBB; //这里有一个隐含Self,完整格式: self.BBB;这里把BBB这个方法赋给ap这个变量,注意BBB与ap的声明原型要一样,不然会有错
        ap(1); 
        ap   :=   CCC; 
        ap(2); 
    end;
      TMouseEvent = procedure(Sender: TObject; Button: TMouseButton; Shift: TShiftState; X, Y: Integer) of object;
      TMouseMoveEvent = procedure(Sender: TObject; Shift: TShiftState; X, Y: Integer) of object;
      TKeyEvent = procedure(Sender: TObject; var Key: Word; Shift: TShiftState) of object;
      TKeyPressEvent = procedure(Sender: TObject; var Key: Char) of object;
      TDragOverEvent = procedure(Sender, Source: TObject; X, Y: Integer; State: TDragState; var Accept: Boolean) of object;
      TDragDropEvent = procedure(Sender, Source: TObject;X, Y: Integer) of object;
      TStartDragEvent = procedure(Sender: TObject; var DragObject: TDragObject) of object;
      TEndDragEvent = procedure(Sender, Target: TObject;X, Y: Integer) of object;
      TDockDropEvent = procedure(Sender: TObject; Source: TDragDockObject;X, Y: Integer) of object;
      TDockOverEvent = procedure(Sender: TObject; Source: TDragDockObject;X, Y: Integer; State: TDragState; var Accept: Boolean) of object;
      TUnDockEvent = procedure(Sender: TObject; Client: TControl;NewTarget: TWinControl; var Allow: Boolean) of object;
      TStartDockEvent = procedure(Sender: TObject;var DragObject: TDragDockObject) of object;
      TGetSiteInfoEvent = procedure(Sender: TObject; DockClient: TControl; var InfluenceRect: TRect; MousePos: TPoint; var CanDock: Boolean) of object;
      TCanResizeEvent = procedure(Sender: TObject; var NewWidth, NewHeight: Integer;var Resize: Boolean) of object;
      TConstrainedResizeEvent = procedure(Sender: TObject; var MinWidth, MinHeight,MaxWidth, MaxHeight: Integer) of object;
      TMouseWheelEvent = procedure(Sender: TObject; Shift: TShiftState; WheelDelta: Integer; MousePos: TPoint; var Handled: Boolean) of object;
      TMouseWheelUpDownEvent = procedure(Sender: TObject; Shift: TShiftState; MousePos: TPoint; var Handled: Boolean) of object;
      TContextPopupEvent = procedure(Sender: TObject; MousePos: TPoint; var Handled: Boolean) of object;

  • 相关阅读:
    20级训练赛Round #5
    【Java】equals 和 == 的区别
    [apue] linux 文件访问权限那些事儿
    用 shell 脚本制造连接频繁中断的场景
    用 shell 脚本做 tcp 协议模拟
    c++ 11 是如何简化你的数据库访问接口的
    使用 shell 脚本自动对比两个安装目录并生成差异补丁包
    Minecraft类游戏地形生成机制
    Aery的UE4 C++游戏开发之旅(5)字符&字符串
    基于随机定位的地图信息获取方式
  • 原文地址:https://www.cnblogs.com/luckForever/p/7254723.html
Copyright © 2020-2023  润新知