首页 > 其他分享 >Delphi7中单元文件内各个部分的执行顺序

Delphi7中单元文件内各个部分的执行顺序

时间:2023-09-18 14:26:30浏览次数:42  
标签:顺序 -- initialization uses form1 窗体 Delphi7 执行 单元

注:本文主要是讨论delphi程序启动时和退出时的执行顺序,期间有些知识来源于Delphi帮助,有些来自《Delphi7程序设计教程》(这本书只告诉我有initialization 和 finalization 这两个关键字,但是没讲明白)(唉,现在的书只讨论框框架架,不讨论细节,写出来的东西让你看能看懂,别人一问或者自己一想,就是什么都不懂!讲的不细致呀!唉,自己琢磨吧!!)。代码用两排‘*’标明。


好了,进入正题,首先说明initialization 和 finalization 在代码单元中的位置:
************************************************************
unit Unit1;

interface

uses
  Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
  Dialogs;

type
  TForm1 = class(TForm)
    Button1: TButton;
    procedure FormCreate(Sender: TObject);
    procedure FormDestroy(Sender: TObject);
  private
    { Private declarations }
  public
    { Public declarations }
  end;

var
  Form1: TForm1;

implementation

uses Unit2;

{$R *.dfm}

procedure TForm1.FormCreate(Sender: TObject);
begin
  ShowMessage('1 FormCreate');
end;

procedure TForm1.FormDestroy(Sender: TObject);
begin
  ShowMessage('1 Destroy');
end;

initialization
  ShowMessage('1 ini');{单元初始化代码}
finalization
  ShowMessage('1 final');{单元退出时的代码}

end.
************************************************************
initialization —— 在单元中放在文件结尾前,包含用来初始化单元的代码,它在主程序运行前运行并且只运行一次。
finalization —— 在单元中放在 initialization 和 end. 之间,包含了单元退出时的代码。在程序退出时运行并且只运行一次。
OnClose —— 在点击关闭按钮或执行该事件时调用。
OnCreate —— 在窗体创建时调用。(我的感觉:该事件是在窗体创建之后,即执行构造函数后才执行的)
OnDestroy —— 在窗体销毁时调用,一般用来销毁程序员自己定义(自己定义、创建,而不是直接从控件板拖拉过来的控件)的对象、变量、指针等等。(与析构函数的关系我还没弄清)

下面是执行顺序(如果程序中没有 initialization、 OnCreate、 OnClose、 OnDestroy、 finalization 中的任何一项,则相应跳过即可):
程序启动 --> 执行 initialization 处的代码 --> 执行窗体的构造函数并创建相应窗体和单元中的对象(如拖拉的控件对象,全局变量等) --> 执行 OnCreate 事件 --> 程序运行 --> 关闭主窗体(此处指调用主窗体的Close或点击主窗体的关闭按钮) --> 执行 OnClose 事件 --> 执行 OnDestroy 事件 --> 执行 finalization 处的代码

以上是对于单个窗体而言,下面是对于多个窗体:
新建一工程,创建3个Form,分别是form1、form2、form3,默认情况下form1为主窗体。
<1 begin>
程序启动 --> 执行 initialization 处的代码(先 form1 然后 form2 最后 form3 ) --> 执行窗体的构造函数并创建相应窗体和单元中的对象(如拖拉的控件对象,全局变量等) --> 执行 OnCreate 事件(先 form1 然后 form2 最后 form3 ) --> 程序运行 --> 关闭主窗体(此处指调用主窗体的Close或点击主窗体的关闭按钮) --> 执行主窗体的 OnClose 事件 --> 执行 OnDestroy 事件(先 form3 然后 form2 最后 form1 ,注意哟,顺序倒过来了。) --> 执行 finalization 处的代码(先 form3 然后 form2 最后 form1 ,注意哟,顺序倒过来了。)
<1 end>
为什么 OnDestroy 和 OnCreate 的顺序相反?为什么  finalization和 initialization 的顺序相反?大家好好想想吧!


另外:如果我在form1中uses 一下Unit2(form2的代码单元)执行顺序如下:
<2 begin>
程序启动 --> 执行 initialization 处的代码(先 form2 然后 form1 最后 form3 ) --> 执行窗体的构造函数并创建相应窗体和单元中的对象(如拖拉的控件对象,全局变量等) --> 执行 OnCreate 事件(先 form1 然后 form2 最后 form3 ) --> 程序运行 --> 关闭主窗体(此处指调用主窗体的Close或点击主窗体的关闭按钮) --> 执行主窗体的 OnClose 事件 --> 执行 OnDestroy 事件(先 form3 然后 form1 最后 form2 ,注意注意,不一样了。) --> 执行 finalization 处的代码(先 form3 然后 form1 最后 form2 ,注意注意,不一样了。)
<2 end>


多个窗体(单元)一些细节性的东西:
1)initialization
initialization 的执行顺序取决于哪个窗体先被调用,对于<1>,由于3个窗体之间没有 uses 和被 uses 的关系,所以按照工程单元uses 中的顺序执行(在工程单元中,如下):
************************************************************
program Project1;

uses
  Forms,
  Unit1 in 'Unit1.pas' {Form1},
  Unit2 in 'Unit2.pas' {Form2},
  Unit3 in 'Unit3.pas' {Form3};

{$R *.res}

begin
  Application.Initialize;
  Application.CreateForm(TForm1, Form1);
  Application.CreateForm(TForm2, Form2);
  Application.CreateForm(TForm3, Form3);
  Application.Run;
end.
************************************************************
如果改变
uses
  Forms,
  Unit1 in 'Unit1.pas' {Form1},
  Unit2 in 'Unit2.pas' {Form2},
  Unit3 in 'Unit3.pas' {Form3};

成为
uses
  Forms,
  Unit2 in 'Unit2.pas' {Form2},
  Unit3 in 'Unit3.pas' {Form3},
  Unit1 in 'Unit1.pas' {Form1};
那么就是(先form2后form3最后form1)
对于<2>,由于form1中uses了Unit2,那么在编译Unit1之前必须先编译Unit2。顺序自然是(先 form2 然后 form1 最后 form3)
所以 initialization 的执行顺序首先看彼此单元之间是否有uses和被uses关系(简单的说就是:调用关系), 然后再看工程文件的uses的顺序。(呵呵,不要被uses弄混了!)

2)OnCreate
OnCreate 的执行顺序由工程单元中的如下类似代码决定
************************************************************
  Application.CreateForm(TForm1, Form1);
  Application.CreateForm(TForm2, Form2);
  Application.CreateForm(TForm3, Form3);
************************************************************
改变之后则相应发生改变。

3)OnDestroy
与OnCreate的顺序相反。(相反时一种对应,创建的顺序与销毁的顺序是相反的,这样是为了避免发生错误,这样也体现了编程要求思维严谨。)

4)finalization
与 initialization 的顺序相反。

再说说OnClose,
当调用窗体的Close或点击关闭按钮时调用该事件。
主窗体Close后,程序就退出。
非主窗体Close,仅仅是Close本窗体。(别说你在OnClose中调用其他窗体的关闭,那些不再讨论范围)

直接用Application.Terminate强制退出程序时,不调用OnClose事件。但 OnDestroy 和 finalization  要执行。

说了这么多,不知道有没有说明白问题。希望大家能领悟(俺表达能力比较差,呵呵~~~)。

 


Trackback: http://tb.blog.csdn.net/TrackBack.aspx?PostId=575307

--------------------- 本文来自 云中雁012345 的CSDN 博客 ,全文地址请点击:https://blog.csdn.net/peixiaobin_blog/article/details/19009627?utm_source=copy 

标签:顺序,--,initialization,uses,form1,窗体,Delphi7,执行,单元
From: https://www.cnblogs.com/zhou0811/p/17711743.html

相关文章

  • 学习后的顺序表(结点内容只设学号、姓名),表内采用数组,数组0位存放数据,相关的函数均按此
    #include<iostream>#include<string.h>usingnamespacestd;typedefstruct{ intid; stringname;}Node;//结点定义typedefstruct{ Node*element;//基地址(动态长度) intlength;//表长}Linklist;#defineMAXSIZE100//最大长度voidmenu();//声明菜单函数voidCreatelist(Lin......
  • vim插件使用python编写+AXI非对齐传输如何发送+verdi配置搜索顺序+verible和verilator
    vim插件使用python编写虽然vim有自己的一套语法格式,但是学习成本放着呢,语言那么多,啥都学哪学的过来嘛。不过vim确实是支持python的,但是是python2,而不是python3,因此语法上的一些问题要兼容下。这个是官方手册,正确而可靠的部分。https://vimdoc.sourceforge.net/htmldoc/if_pyth......
  • 消息队列中如何保证消息的顺序性?
    面试官心理分析其实这个也是用MQ的时候必问的话题,第一看看你了不了解顺序这个事儿?第二看看你有没有办法保证消息是有顺序的?这是生产系统中常见的问题。面试题剖析我举个例子,我们以前做过一个mysql binlog 同步的系统,压力还是非常大的,日同步数据要达到上亿,就是说数据从一个mys......
  • 页面中点击按钮需要新建轮播(需要新建多个),出现顺序错乱的问题
    当页面中通过点击按钮切换轮播,即点击按钮需要newswiper,新建后,页面中swiper内容没有问题但是,点击上一个下一个按钮,顺序会发生错乱 在new之前需要使用destroy销毁 ......
  • ActiveWorkbook工作簿后修改工作表中单元格的数值
    Sub新建写入重命名()Workbooks.Add'内置名称报错'ActiveWorkbook.Sheet1.Range("a2").Value="孙"'索引'ActiveWorkbook.Sheets(1).Range("a2").Value="孙"'名称'ActiveWorkbook.Sheets("Sheet1").Range(&......
  • pytest单元测试框架(集成篇)
    一、@pytest.mark.parametrize()基本用法 @pytest.mark.parametrize(args_name,args_value)args_name:参数名args_value:参数值(列表[],元祖(),字典列表[{},{}],字典元祖({},{})),有多个值用例就会执行多少次importtimeimportpytestclassTestApi:@pytest.mark.par......
  • 聊一聊ZooKeeper的顺序一致性(转)
    addbyzhj: 原文有音频朗读原文:https://time.geekbang.org/column/article/239261作者:极客视点你好,欢迎收听极客视点。ZooKeeper作为分布式应用系统协调服务,在分布式系统中的应用非常广泛,在某些业务场景下甚至可以作为注册中心、分布式锁来使用。ZooKeeper之所以能有如此......
  • pytest单元测试框架(升华篇)
    -----------------------------------Pytest框架实现一些前后置(固件,夹具)的处理,常用三种一、setup/teardown,setup_class/teardown_class所有为什么需要这些功能?比如:web自动化执行用例之前,请问需要打开浏览器吗?用例执行后需要关闭浏览器?classTestMay:#这个在所有的用例......
  • EndNote调整中文、英文参考文献的排序顺序
      本文介绍在EndNote软件中,使得参考文献按照语种排列,中文在前、英文在后的方法。  前期我们在文献管理EndNote软件自定义修改引文输出格式的方法一文中,详细介绍了文献管理软件EndNote的引用格式自定义方法,其中我们设置了将参考文献部分的文章按照文章语种进行排序,而这一设置在......
  • 二维数组的存储顺序、表示方法
    二维数组的存储顺序、表示方法先说一维数组:1.数组首地址也是第一个元素的首地址1#include<iostream>2usingnamespacestd;34intmain(){5intarr[5]={};6cout<<"arr="<<arr<<endl;7cout<<"&arr[0]=&q......