主程序界面的菜单中有一个菜单项目负责调用一个窗口CustomerKindForm;当这个窗口OnCreate的时候调用一个方法,如下:
procedure TCreditLevelForm.FormCreate(Sender: TObject);
begin
  Self.InitInterface ;
end;InitInterface方法代码如下:
procedure TCreditLevelForm.InitInterface;
begin
  ComboBox1.ItemIndex:=0;
  Edit2.Text :=InfoManager.GetMaxCode('Dict_CreditConfig');
  with DBGrid1,Self.Frame21.ADOQuery1 do
  begin
    Columns[0].FieldName := 'XinYuLX';
    Columns[1].FieldName := 'XinYuBM';
    Columns[2].FieldName := 'XinYuMC';
    Columns[3].FieldName := 'QiShiZhi';
    Columns[4].FieldName := 'ZhongZhiZhi';
    Columns[5].FieldName := 'ZhuXiaoBS';
    InfoManager.ShowCreditLevelData ;  //当执行到这里的时候调用类TInfoManager的方法来在DBGrid中显示相关数据
                                       //类TInfoManager在单元ModuleFrame中定义,并且在此单元定义全局变量InfoManager
  end;
  Self.SetFocusedControl(Edit4);
end;ShowCreditLevelData方法代码如下:
procedure TInfoManager.ShowCreditLevelData;
begin
  with CreditLevelForm.Frame21.ADOQuery1 do  //执行到这里马上报一个内存访问错误,为什么?
  begin
    Close;
    SQL.Text:='Select *,'+
              'XinYuLX=Case XinYuLB '+
              'When 0 Then ''供应商'' '+
              'When 1 Then ''承运商'' '+
              'Else ''客户'' End,'+
              'ZhuXiaoBS=case ZhuXiaoBZ '+
              'When 1 Then ''√'' '+
              'When 0 Then ''''End '+
              'From Dict_CreditConfig';
    Open;
  end;
end;

解决方案 »

  1.   

    adoquery的connection是如何处理的。
      

  2.   

    呵呵,你到底是用了frame了在Frame2的单元中写一个方法
    with ADOQuery1 do  
     begin
        Close;
        SQL.Text:='Select *,'+
                  'XinYuLX=Case XinYuLB '+
                  'When 0 Then ''供应商'' '+
                  'When 1 Then ''承运商'' '+
                  'Else ''客户'' End,'+
                  'ZhuXiaoBS=case ZhuXiaoBZ '+
                  'When 1 Then ''√'' '+
                  'When 0 Then ''''End '+
                  'From Dict_CreditConfig';
        Open;
      end;
    然后在ShowCreditLevelData中调用这个方法试试
      

  3.   

    类TInfoManager在单元ModuleFrame中定义CreditLevelForm.Frame21.ADOQuery1 你在类中访问实例,当然出错了!!!
    CreditLevelForm.Frame21是frame的实例
      

  4.   

    可能是由于这段代码在form的oncreate事件中执行的原因,你应该在create事件里只用postmessage发一个将要执行Self.InitInterface ;的消息,是这个过程在窗体创建完后稍后再来执行这个过程
      

  5.   

    垃圾AD,你说的可能有道理啊。我在InfoManager.ShowCreditLevelData;这句前用Assigned进行检测就不出错,但如果放到ShowCreditLevelData方法内部马上就报错,我正纳闷了,给我讲讲!我现在加分去!
      

  6.   

    好了,加到50了,AD,快给我说说啊!这个GS,想宰我?!
      

  7.   

    我New----Frame定义了一个TFrame2类,然后我在CreditLevelForm中进行引用,这样在TCreditLevelForm的类申明中就有了这样的部分:Frame21: TFrame2;
    然后我在另外一个单元中定义类TInfoManager,最后给其设计一个方法访问CreditLevelForm上的对象Frame21,就这么一个过程!但在这个方法ShowCreditLevelData中老是报内存访问错误!
      

  8.   

    //类TInfoManager在单元ModuleFrame中定义,并且在此单元定义全局变量InfoManager
    这个应该是在Tframe2里定义的吧?procedure TInfoManager.ShowCreditLevelData;
    begin
      with CreditLevelForm.Frame21.ADOQuery1 do 
    你这样就好比是这样TA=Class
     procedure aa;
    end;TB=class
     a:Ta;
     procedure bb;
    end;var b:Tb;procedure Ta.aa;
       b.bb;
    end;
    你觉得这段代码有什么问题?
      

  9.   

    myling(阿德) 高,实在是高!
      

  10.   

    :) fs 看到你的消息了老在qq里催 正在看
      

  11.   

    当点了相应菜单项调用CreditLevelForm时,首先创建窗体,当创建的时候触发OnCreate事件,如下:
    procedure TCustomerKindForm.FormCreate(Sender: TObject);
    begin
      Self.InitInterface ;
    end;接着,进入InitInterface过程,如下:
    procedure TCustomerKindForm.InitInterface;
    begin
      ComboBox1.ItemIndex:=0;
      Edit2.Text := InfoManager.GetMaxCode('Dict_CustomerKind');
      with DBGrid1,CustomerKindForm.Frame21.ADOQuery1 do
      begin
        Columns[0].FieldName :='KeHuLX';
        Columns[1].FieldName :='LeiBieBM';
        Columns[2].FieldName :='LeiBieMC';
        Columns[3].FieldName :='ZhuXiaoBS';
        if Assigned(Self.Frame21.ADOQuery1  ) then  //到这里可以显示一个对话框
          ShowMessage('Exists');
        InfoManager.ShowCustomerData ;  //从这里进入ShowCustomerData方法
      end;
      Self.SetFocusedControl(Edit2);
    end;最后进入ShowCustomerData方法,如下:
    procedure TInfoManager.ShowCustomerData;
    begin
      if Assigned(CustomerKindForm.Frame21.ADOQuery1  ) then  //这里报内存访问错误!
          ShowMessage('Exists');  
      with CustomerKindForm.Frame21.ADOQuery1 do
      begin
        Close;
        SQL.Text:='Select *,'+
                  'KeHuLX=Case KeHuLB '+
                  'When 0 Then ''供应商'' '+
                  'When 1 Then ''承运商'' '+
                  'Else ''客户'' End,'+
                  'ZhuXiaoBS=case ZhuXiaoBZ '+
                  'When 1 Then ''√'' '+
                  'When 0 Then ''''End '+
                  'From Dict_CustomerKind';
        Open;
      end;
    end;------------------------------------------------------------
    各位帮忙看看为什么?脑袋都大了!
      

  12.   

    ShowMessage('Exists');
    informanager创建了没有????
        InfoManager.ShowCustomerData ;
      

  13.   

    你在雷里转圈圈阿  把自己都转进去了
    procedure TInfoManager.ShowCustomerData;
    begin
      if Assigned(CustomerKindForm.Frame21.ADOQuery1  ) then  //这里报内存访问错误!
          ShowMessage('Exists');  
    ////////////////Frame21是在那里定义的?------》我New----Frame定义了一个TFrame2类,然后我在CreditLevelForm中进行引用,这样在
     TCreditLevelForm的类申明中就有了这样的部分:Frame21: TFrame2;//////////
    然后我在另外一个单元中定义类TInfoManager,最后给其设计一个方法访问CreditLevelForm上
    的对象Frame21,
    ///////////////
    TInfoManager里没有Frame21的实例阿  你这样调用它的方法不出错才怪
      

  14.   

    完整代码执行顺序如下(楼上各位好象都不清楚执行顺序!):首先点菜单,执行菜单项的OnClick事件,由于用了ActionList所以执行的是对应Action的OnExecute实践,如下
    procedure TMainForm.Action18Execute(Sender: TObject);
    begin
      gError:=SetCreditLevel;  //SetCreditLevel是CreditLevelForm的一个独立的函数
      if gError<>'' then
      begin
        Application.MessageBox(PChar(gError),'错误',MB_ICONERROR+MB_OK);
        Exit;
      end;
    end;
    其中SetCreditLevel代码如下
    function SetCreditLevel:String;
    var
      vErrStr:String;
    begin
      vErrStr:='';
      if not CommonFunc.IsExistForm('CreditLevelForm') then
        try
          CreditLevelForm:=TCreditLevelForm.Create(Application);
        except
          vErrStr:='调用车辆信誉等级窗口错误.';
          Result:=vErrStr;
          Exit;
        end;  
    end;
    其中再次调用CommonFunc单元的独立方法IsExistForm来判断名为'CreditLevelForm'的窗体是否当前存在,如果返回False,说明不存在,动态创建。IsExistForm函数代码如下
    function IsExistForm(AFormName:String):Boolean;
    var
      I:Integer;
    begin
      Result:=False;
      for I:=0 to Screen.FormCount-1 do
        if Screen.Forms[I].Name=AFormName then
        begin
          Result:=True;
          Break;
        end
    end;到这里开始触发CreditLevelForm的OnCreate事件,如下
    procedure TCreditLevelForm.FormCreate(Sender: TObject);
    begin
      Self.InitInterface ;
    end;接着进如初始化界面的过程,如下
    procedure TCreditLevelForm.InitInterface;
    begin
      ComboBox1.ItemIndex:=0;
      Edit2.Text :=InfoManager.GetMaxCode('Dict_CreditConfig');
      with DBGrid1,Self.Frame21.ADOQuery1 do
      begin
        Columns[0].FieldName := 'XinYuLX';
        Columns[1].FieldName := 'XinYuBM';
        Columns[2].FieldName := 'XinYuMC';
        Columns[3].FieldName := 'QiShiZhi';
        Columns[4].FieldName := 'ZhongZhiZhi';
        Columns[5].FieldName := 'ZhuXiaoBS';
        //行位置一
        InfoManager.ShowCreditLevelData ;  //这里跳转
      end;
      Self.SetFocusedControl(Edit4);
    end;初始化的后期跳转到在另外一个单元定义的一个类TInfoManager的方法ShowCreditLevelData的代码上,如下
    procedure TInfoManager.ShowCreditLevelData;
    begin
      //行位置二
      with CreditLevelForm.Frame21.ADOQuery1 do  //然后在这里出错!为什么?
      begin
        Close;
        SQL.Text:='Select *,'+
                  'XinYuLX=Case XinYuLB '+
                  'When 0 Then ''供应商'' '+
                  'When 1 Then ''承运商'' '+
                  'Else ''客户'' End,'+
                  'ZhuXiaoBS=case ZhuXiaoBZ '+
                  'When 1 Then ''√'' '+
                  'When 0 Then ''''End '+
                  'From Dict_CreditConfig';
        Open;
      end;
    end;-----------------------------------------------------------
    如果我在上述代码的行位置一和二处分别加语句
    if Assigned(CreditLevelForm.Frame21.ADOQuery1) then
      ShowMessage('Exist');
    然后单步调试,在位置一上可以显示,但到了位置二马上就报一个内存访问错误,很是蹊跷!
      

  15.   

    procedure TCustomerKindForm.InitInterface;----》TCustomerKindForm现在在他这里
    begin
      ComboBox1.ItemIndex:=0;
      Edit2.Text := InfoManager.GetMaxCode('Dict_CustomerKind');
      with DBGrid1,CustomerKindForm.Frame21.ADOQuery1 do
      begin
        Columns[0].FieldName :='KeHuLX';
        Columns[1].FieldName :='LeiBieBM';
        Columns[2].FieldName :='LeiBieMC';
        Columns[3].FieldName :='ZhuXiaoBS';
        if Assigned(Self.Frame21.ADOQuery1  ) then  //到这里可以显示一个对话框
          ShowMessage('Exists');
        InfoManager.ShowCustomerData ; ---》这里调用InfoManager类方法
    ///////////
    TCustomerKindForm是从这里进入的InfoManager
      

  16.   

    procedure TInfoManager.ShowCustomerData( TCustomerKindForm aForm );
    begin
      if Assigned(aForm.Frame21.ADOQuery1  ) then  //  这样总该可以了吧
          ShowMessage('Exists');  
      

  17.   

    To pingshx  创建了!To duxin  TInfoManager里面是没有Frame21的实例,但我在访问Frame21之前前面是加了限定符的:  with CreditLevelForm.Frame21.ADOQuery1 do  //注意,这里加了限定符号CreditLevelForm  
        ....
      

  18.   

    To pingshx  创建了!To duxin  TInfoManager里面是没有Frame21的实例,但我在访问Frame21之前前面是加了限定符的:  with CreditLevelForm.Frame21.ADOQuery1 do  //注意,这里加了限定符号CreditLevelForm  
        ....
      

  19.   

    To Raptor  如果我那里通过参数往里传窗体,还没有试验。但我不明白为什么直接访问那里就出错?
      

  20.   

    procedure TCreditLevelForm.InitInterface;
    begin
      ComboBox1.ItemIndex:=0;
      Edit2.Text :=InfoManager.GetMaxCode('Dict_CreditConfig');
      with DBGrid1,Self.Frame21.ADOQuery1 do
    //////
    在这里没有错 因为Frame21是属于TCreditLevelForm的方法这样像阿德说的 ta=class
                    方法a你想在tb=class里
           ta.方法a
    这是不行的要么  tb里
       xx=ta.Create
       xx.方法a在一个类中对其他的类的控制权只有 通过实例来控制
    如果想达到你要的效果 xx=ta.Create
                         xx.方法a 这样也不行他是同态建立所以你可以在TCustomerKindForm里写一个方法返回
    Assigned(Self.Frame21.ADOQuery1  )
      

  21.   

    靠 写了半天 没发出去  破csdn
      

  22.   

    靠,搞了半天他是这样声明的,这个了色,也不说清楚
    (2003-09-05 16:10:42)    FrameSniper
    现在是三个单元申明三个东西
    ModuleDM----TFrame2
    CreditLevelFrm----TCreditLevelForm
    ModuleFrame----TInfoManager
      

  23.   

    procedure TCustomerKindForm.InitInterface;----》TCustomerKindForm现在在他这里
    begin
      ComboBox1.ItemIndex:=0;
      Edit2.Text := InfoManager.GetMaxCode('Dict_CustomerKind');
      with DBGrid1,CustomerKindForm.Frame21.ADOQuery1 do
      begin
        Columns[0].FieldName :='KeHuLX';
        Columns[1].FieldName :='LeiBieBM';
        Columns[2].FieldName :='LeiBieMC';
        Columns[3].FieldName :='ZhuXiaoBS';
        if Assigned(Self.Frame21.ADOQuery1  ) then  
    //////////
    在这里没错
    因为Frame21是TCustomerKindForm的方法 可以Self.Frame21.ADOQuery1  这样来用
    但是在TInfoManager中
    procedure TInfoManager.ShowCreditLevelData;
    begin
      //行位置二
      with CreditLevelForm.Frame21.ADOQuery1 do  这样用就是阿德说的  ta=class
                         方法a
    你想在tb中     tb=class
                   ta.方法a
    这样是不行的 在一个类中对其他类的控制权只能通过实例               比方 tb=class
                     xx=ta.Create
                     xx.方法a这样动态建立又不能达到你的效果
    所以你最好在TCustomerKindForm中建一个方法返回CustomerKindForm.Frame21.ADOQuery1的值
      

  24.   

    重新看了一遍你的代码,我问题跟我在QQ里说的不同,应该是这样:你执行到出错的地方时,FormCreate事件还没有执行完成,即:      CreditLevelForm:=TCreditLevelForm.Create(Application);这一句还没有执行完,此时CreditLevelForm这个变量还是空的,而你在出错处却引用了它,当然会出AV错了。改成用参数传的话:    InfoManager.ShowCreditLevelData( Self );  //这里跳转procedure TInfoManager.ShowCreditLevelData( TCreditLevelForm aForm );
    begin
      //行位置二
      with aForm.Frame21.ADOQuery1 do  //然后在这里出错!为什么?因为构造函数已经执行,Self已经存在,所以应该就可以了。
      

  25.   

    这句话
    Self.SetFocusedControl(Edit4);
    好象也不对
      

  26.   

    不对,小伍,你说的意思和猛禽说的不是一回事情,他的意思是虽然我这里可以通过Assigned方法来检测对象指针不为空,但这里可能是一个非空但没有意义的指针,所以如果是这样,就会报错!而我现在想问题可能也就出在这里,让我再想想!
      

  27.   

    靠 本来就是两种方法实现一个目的就是了  要不就是调用类本身返回你想要的结果  要不就是传指针取得对类的访问控制权传指针当然有代价类没有建立传self 也会有危险
      

  28.   

    娘的,我突然想到一个问题! 你的table是放在窗体的frame里,还是在Frame的窗体上添加的? 就是你设计的时候,是往Frame2上放的,还是往Frame21上放的? 很可能是这个问题 仔细检查一下,会不会是哪一下你疏忽了,顺手放在了form的frame上 你到frame单元,然后F12切换一下,仔细检查检查 要真是这个错,你就一死以谢天下吧
      

  29.   

    To 猛禽,小伍  如果按照你们的想法,就是说由于调用TCreditLevelForm.Create方法而触发CreditLevelForm的OnCreate中的代码,这个时候CreditLevelForm这个对象指针是没有意义的!
      但如果我在CreditLevelForm的OnCreate的第一句换成
      ShowMessage(Self.Caption);这里也可以显示成功,和你们说的想矛盾,因为如果CreateLevelForm没有意义,就说明栈上的对象不存在,因为TCreditLevelForm.Create没有执行完成。这样肯定取不到Caption这个值了,因为这个值是存放在栈中的!但实际是在执行OnCreate的代码前是可以取到的,这就说明在触发这个事件的代码前所有的对象都是创建了的!所以在执行到我出错的地方的时候CreditLevelForm这个对象指针是早已有意义的!  况且,可以看到在InitInterface方法的开始我就访问了CreditLevelForm上的ComboBox1和Edit2,如果说CreditLevelForm这个指针没有意义,那么是根本访问不了这两个控件的!  所以,个人感觉答案尚不明确!期待中.........
      

  30.   

    我以前一直认为,在触发OnCreate事件中的代码之前,Self对应对象以及其上所有的控件都应该是已经创建的。这个问题《高手突破》上有明确的解释,但我想不起来了!刚才刚实验了,个人认为我这个猜想是正确的,比如在OnCreate的第一句加上
    ShowMessage(Self.Name);这样的句子,这里访问的是私有数据,而私有数据是存放在栈上的对象实体空间中的,如果说在触发OnCreate事件前对象不存在,那么是根本无法访问这些私有数据的。因此,在触发前对象是已经创建的!
      

  31.   

    ta=class---------------------------->TCreditLevelForm
    方法a   ----------------------------->Frame21.ADOQuery1tb=class----------------------------->TInfoManager
    ta.方法a------------------------------>CustomerKindForm.Frame21.ADOQuery1
    感觉出不对来了吧 一个类调用另一个类   1我说的实例    2猛禽的传控制权
    procedure TInfoManager.ShowCreditLevelData;
    var 
      xx:TCreditLevelForm
    begin
      //行位置二  xx:=TCreditLevelForm.creat
      with xx.Frame21.ADOQuery1 do  这样就是通过实例引用了 
    猛禽的传值不失一个好方法 但现在麻烦就是在creat传递self 我个人同意你的观点
    在栈里很多东西都没有初始化如果不是在 creat里 那我想应该没问题
      

  32.   

    可是我的类结构不是这样样子啊!我结构和文件结构如下:1.单元CreditLevelFrm.pas里面
    unit CreditLevelFrm
    ....
    TCreditLevelForm=class(TForm)
    ....
    Frame21:TFrame2;
    procedure InitInterface;
    procedure FormCreate(Sender: TObject);
    ....
    end;
    ....
    procedure TCreditLevelForm.InitInterface;
    begin
      ....
      InfoManager.ShowCreditLevelData ;
      ....
    end;
    procedure TCreditLevelForm.FormCreate(Sender:TObject);
    begin
      Self.InitInterface ;
    end;2.单元ModuleFrame.pas里面:
    unit ModuleFrame
    ....
    TInfoManager=class
      ....
      procedure InitInterface;
      ....
    end;
    ....
    procedure TInfoManager.ShowCreditLevelData;
    begin
      with CreditLevelForm.Frame21.ADOQuery1 do  //a AV fault here!
        ....
    end;3.单元ModuleDM.pas里面:
    unit ModuleDM;interfaceuses
      Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms, 
      Dialogs, DB, ADODB, SysDM;type
      TFrame2 = class(TFrame)
        ADOQuery1: TADOQuery;
        DataSource1: TDataSource;
      private
        { Private declarations }
      public
        { Public declarations }
      end;implementation{$R *.dfm}end.
    以上就是我的单元结构,小伍!和你说的不一样哦!
      

  33.   

    靠,晕!!!这么长的代码懒得看,有些代码在OnCreate中写是会出问题的,特别是用TFrame时,你最好移到OnShow中试试。
      

  34.   

    TO: FrameSniper(§好好学习 天天向上§) 
    你的理解还是不对,再把偶们几个的跟贴仔细看看吧。^_^
      

  35.   

    是啊,就向我上面写的一样,不应该写在oncreate里,可以通过post一个消息来解决
      

  36.   

    procedure TInfoManager.ShowCreditLevelData;
    begin
      with CreditLevelForm.Frame21.ADOQuery1 do  //执行到这里马上报一个内存访问错误,
      //..
    end;CreditLevelForm 创建了吗?报内存访问错误,多半是访问了一个不存在的对象或者指针,
    To myling(阿德): 
    //类TInfoManager在单元ModuleFrame中定义 
    //CreditLevelForm.Frame21.ADOQuery1 
    //你在类中访问实例,当然出错了!!!在类中访问类实例会报错吗 ?
    我经常在一个类中访问这个类的一个实例,不会报错啊,
     
      

  37.   

    还有,InfoManager 是不是创建了?
      

  38.   

    这么产的代码真的很难读懂,就分析下面的(你所提供的)例子吧
    TA=Class
     procedure aa;
    end;TB=class
     a:Ta;
     procedure bb;
    end;var b:Tb;
    procedure Ta.aa;
       b.bb;
    end;
    我认为出错的地方有:
    1,a:Ta在tb类的create中没有创建;
    2,b:Tb定义为全局变量,而且ta操纵的是固定了的b:Tb这一个全局变量;
    你的程序中b是数据模块或者窗体,是否这些数据模块或者窗体已经创建了?(一定要是application.CrateForm()这样的创建形势,即b作为全局变量创建,不能是在汉书或者过程中的局部变量)
    3, 同意huojiehai(海天子) ,将代码最好移到OnShow中试试
        不同意hkbarton(宁静至远||淡泊明志) 的,不必通过post一个消息来解决
    4,Frame与本问题关系并不大,如果该单元中并没有于特定变量相关的代码,即使有,如果这些变量是真正的全局变量,也无所谓。
      

  39.   

    FrameSniper:  搞定了吗?procedure TInfoManager.ShowCreditLevelData;
    begin
      with CreditLevelForm.Frame21.ADOQuery1 do  //执行到这里马上报一个内存访问错误,
     ...
    end对了,这样写是很容易报错的,在一个类里面直接引用另外一个类的实例,
    要是把 CreditLevelForm 通过参数传递进来,
    在访问 CreditLevelForm前先判断一下是不是创建了这个类的实例,
    这样可能会安全些。
      

  40.   


      with CreditLevelForm.Frame21.ADOQuery1 do  这三个变量中总有一个是没有创建的.
      

  41.   

    FrameSniper,怎么样了啊?
      

  42.   

    To Hkbarton
      
      如何Post,可以说的详细点吗?To 云意  还没有,乱套了,脑子都乱了,明天调试吧!脑子糊涂了!
      

  43.   

    下班的时候,在位置二上给加了个代码
    if not Assigned(CreditLevelForm) then ShowMessage('Exist');结果这里居然出现,乱套了!
      

  44.   

    你的 CreditLevelForm 应该是 TCreditLevelForm 类型的全局变量吧? 当初始化 CreditLevelForm 这个全局变量时,依次调用了 TCreditLevelForm.FormCreate ==> TCreditLevelForm.InitInterface ==> TInfoManager.ShowCreditLevelData,但是 TInfoManager.ShowCreditLevelData 却需要访问 CreditLevelForm ,而 CreditLevelForm 并没有初始化完成,所以就出现了内存访问错误!  一家之言,不知道是不是如此?
      

  45.   

    vpost一个消息后,就可以使窗体创建完后再执行你的代码,大家都知道post和send的区别,用postmessage,接收到消息的消息处理过程不会马上执行,而是等待前面的消息处理完以后,这样当真正执行ShowCreditLevelData时,该创建的东西和该初始化的东西已经创建和初始化了,就不会有错误
    我认为比如说()
    var
     WM_ShowCreditLevelData=WM_USER+1000;
    procedure TCreditLevelForm.FormCreate(Sender: TObject);
    begin
      postmessage(handle,WM_ShowCreditLevelData,0,0);//
    end;
    然后在定义一个处理这个消息的过程
    procedure WMShowCreditLevelData(var msg:Tmessage);//messageWM_ShowCreditLevelData
    begin
     Self.InitInterface ;
    end;
      

  46.   

    真的不妨试试上面的方法,正如eapmars(流铭)所说的一样,等待CreditLevelForm初始化完成后才能访问它,而上面的方法就可以实现这个等待过程
      

  47.   

    我也碰到过在 OnCreate 事件中出错的情况,用 PostMessage 处理了
      

  48.   

    刚才花了点时间看了看前面各位的回复,其实猛禽兄已经指出问题所在了。楼主现在的认识还存在问题: 在 OnCreate 中可以通过 Self 来访问窗体的各种属性、组件,这并没有错,但此时 CreditLevelForm 这个全局变量和 Self 还是两码事。在这个时候 Self 还没有赋值给 CreditLevelForm  ,所以 CreditLevelForm = nil。因此当你添加了 if not Assigned(CreditLevelForm) then ShowMessage('Exist'); 这个语句时,会出现消息框提示!
      

  49.   

    靠 了色
    今天早上好很兴奋的告诉我,找到原因了因为 Frame21没创建我回的帖子反复强调 你要创建实例 要不就像猛禽传递指针这家伙到地仔细看帖子了没有  靠 大家不要回了
      

  50.   

    ……哈哈哈哈哈哈哈哈哈。我看着帖子就想笑,一直笑到最后!中间几个人的做法都很不错,可是FS就想傻了似的绕圈子绕不出来。lolFS的笑料很不错哦。-_-|
      

  51.   

    REALLIKE,大话说不得!我现在就问你们一个问题,如下:procedure TCreditLevelForm.InitInterface;
    begin
      ComboBox1.ItemIndex:=0;    //1
      Edit2.Text := InfoManager.GetMaxCode('Dict_CustomerKind');  //2
      with DBGrid1,CreditLevelForm.Frame21.ADOQuery1 do  //3
      begin
        Columns[0].FieldName :='KeHuLX';
        Columns[1].FieldName :='LeiBieBM';
        Columns[2].FieldName :='LeiBieMC';
        Columns[3].FieldName :='ZhuXiaoBS';
        InfoManager.ShowCustomerData ;
      end;
      Self.SetFocusedControl(Edit2);
    end;上面代码是InitInterface的代码,行1、2和3处,如果我按F4到行1上停止,这个时候我把鼠标分别放到行1的ComboBox1上看到RTTI给返回内容,可以访问;接着我把鼠标放到行2的Edit2上看到RTTI继续给返回内容,表示也可以访问;接着,我把鼠标放到行3的CreditLevelForm上,RTTI也给返回表示可以访问,但是个空值(这个很正常,全局的非简单类型变量要进行初始化的,所以这里为空Nil);但最后当我把鼠标放到Frame21上的时候,却提示是无法访问的,也就说明这个对象根本还没有建立!这里就有个奇怪的问题,为什么ComboBox1、Edit2和Frame21都是CreditLevelForm上的控件,但到了这个地方前两个可以访问,后一个却无法访问,而且都是在CreditLevelForm为Nil的情况下?谁来给我解释解释为什么?另外一个问题就是更正我以前的一个看法:在触发OnCreate事件的时候所有的对象是没有创建的!在OnCreate里面访问Self不会出错,但访问自身变量名称马上出错!谁来解释一下什么时候开始访问二者就等价了?
      

  52.   

    FS…… 我建议你经常性的使用delphi的各种debug工具,来跟踪一下。因为你说的问题,我也是用那些工具来找的,为什么不试试看呢?三分编,七分调。俺来这里打个逛。:〉
      

  53.   

    调试工具里面我唯一不会使用的就是CPU窗口!但调试的目的是为了超出错误,找出错误的目的是为了解决错误,而解决错误的过程就需要我们了解原理,这个才是最重要的,否则下次碰到还是一样,你说呢?好了,继续等待各位的意见!
      

  54.   

    好了,问题解决了,有时间写个东西大家看看,这个地方比较绕啊!开始揭贴!本帖除了AD,HKBarton,DuXin,Raptor,云意,ZhxfZhxt1,LeapMars外
    AD,HKBarton,DuXin,Raptor,LeapMars每个赠送200分!谢谢各位积极参与,让俺认识到自己犯的一个概念错误,呵呵.........