Best practice to do nested TRY / FINALLY statement

前端 未结 6 992
逝去的感伤
逝去的感伤 2020-12-04 16:07

Hi What is the best way to do nested try & finally statements in delphi?

var cds1  : TClientDataSet;
    cds2  : TClientDataSet;
    cds3  : TClientDataS         


        
6条回答
  •  -上瘾入骨i
    2020-12-04 16:29

    I'd use something like this:

    var
      Safe: IObjectSafe;
      cds1 : TClientDataSet;
      cds2 : TClientDataSet;
      cds3 : TClientDataSet;
      cds4 : TClientDataSet;
    begin
      Safe := ObjectSafe;
      cds1 := Safe.Guard(TClientDataSet.Create(nil)) as TClientDataSet;
      cds2 := Safe.Guard(TClientDataSet.Create(nil)) as TClientDataSet;
      cds3 := Safe.Guard(TClientDataSet.Create(nil)) as TClientDataSet;
      cds4 := Safe.Guard(TClientDataSet.Create(nil)) as TClientDataSet;
      ///////////////////////////////////////////////////////////////////////
      ///      DO WHAT NEEDS TO BE DONE
      ///////////////////////////////////////////////////////////////////////
    
      // if Safe goes out of scope it will be freed and in turn free all guarded objects
    end;
    

    For the implementation of the interface see this article, but you can easily create something similar yourself.

    EDIT:

    I just noticed that in the linked article Guard() is a procedure. In my own code I have overloaded Guard() functions that return TObject, above sample code assumes something similar. Of course with generics much better code is now possible...

    EDIT 2:

    If you wonder why try ... finally is completely removed in my code: It's impossible to remove the nested blocks without introducing the possibility of memory leaks (when destructors raise exceptions) or access violations. Therefore it's best to use a helper class, and let the reference counting of interfaces take over completely. The helper class can free all objects it guards, even if some of the destructors raise exceptions.

提交回复
热议问题