AGB  ·  Datenschutz  ·  Impressum  







Anmelden
Nützliche Links
Registrieren
Thema durchsuchen
Ansicht
Themen-Optionen

Class Factory Problem

Ein Thema von Ghostwalker · begonnen am 29. Apr 2018 · letzter Beitrag vom 29. Apr 2018
 
Ghostwalker

Registriert seit: 16. Jun 2003
Ort: Schönwald
1.299 Beiträge
 
Delphi 10.3 Rio
 
#1

Class Factory Problem

  Alt 29. Apr 2018, 09:29
MoinMoin,

ich beschäftige mich grad mit dem Factory Pattern in zusammenhang mit Klassen. Ich hab mir auch verschiedene Beiträge hier in der DP sowie im Netz durchgelesen. Aber irgendwie bekomme ich es nicht hin.

Hier die Manager-Klasse:

Delphi-Quellcode:
unit Demo.Manager;

interface
uses
  System.Classes,
  System.Generics.Collections,
  Demo.Interfaces;

TYPE
  TManagerEntry = Record
                   TheClass : TClass;
                   TheInst : TObject;
  End;

  MyManager = Class
  private
    class var fClasses:TDictionary<STRING,TManagerEntry>;
  protected
    Class Constructor Create;
    Class Destructor Destroy;
  Public
    Class Procedure RegisterEntry(Ident:String;AClass:TClass);
    Class function GetEntry(Ident:String):ITestInterface;
  End;

implementation
uses
  System.TypInfo,
  System.RTTI,
  System.SysUtils,
  Demo.Classes;

Class Constructor MyManager.Create;
begin
  fclasses := TDictionary<STRING,TManagerEntry>.create;
end;

Class Destructor MyManager.Destroy;
begin
  fclasses.free;
end;

Class Procedure MyManager.RegisterEntry(ident:string;AClass:TClass);
var
  tmp : TManagerEntry;

begin
  if (fclasses.containsKey(ident)) then
    Raise Exception.Create(ident+' is already registered !');
  if (Supports(AClass,ITestInterface)) then
  begin
    tmp.TheClass := AClass;
    tmp.TheInst := NIL;
    fclasses.add(ident,tmp);
  end;
end;

Class function MyManager.GetEntry(ident:string):ITestInterface;
var
  hlp : TManagerEntry;

  function CreateMyIntf(AClass:TClass):TObject;
  var
    ctx: TRttiContext;
    RT: TRttiType;
    Value: TValue;
    RM: TRttiMethod;
    ParamList: TList<TValue>;
    RP: TRttiParameter;

  begin
    result := NIL;
    ctx := TRttiContext.Create;
    RT := ctx.GetType(AClass);
    for rm in rt.GetMethods do
    begin
      if rm.IsConstructor then
      begin
        ParamList := TList<TValue>.Create;
        for rp in rm.GetParameters do
        begin
          TValue.Make(0, rp.ParamType.Handle, Value);
          ParamList.Add(Value);
        end;
        result := rm.Invoke(AClass,ParamList.ToArray).AsObject;
        ParamList.Free;
        break;
      end;
    end;
  end;

begin
  result := NIL;
  if (fclasses.ContainsKey(ident)) then
  begin
    hlp := fclasses[ident];
    if (hlp.TheInst = NIL) then
      hlp.TheInst := CreateMyIntf(hlp.TheClass);
    Supports(hlp.TheInst,ITestInterface,result);
  end;
end;

end.
Hier die Demoklassen, die ein entsprechendes Interface implementieren:
Delphi-Quellcode:
unit Demo.Classes;

interface
uses
  System.Classes,
  Demo.Interfaces,
  Demo.Manager;

Type
  TDemoClass1 = Class(TInterfacedObject,ITestInterface)
    public
      Procedure TuWas(Strings:TSTrings);
  End;

  TDemoClass2 = Class(TInterfacedObject,ITestInterface)
  public
    Procedure TuWas(Strings:TStrings);
  end;

  TDemoClass3 = Class(TInterfacedObject,ITestInterface)
  public
    Procedure TuWas(Strings:TStrings);
  end;


implementation


Procedure TDemoClass1.TuWas(Strings:TStrings);
begin
  Strings.append('1. Demo Klasse');
end;

Procedure TDemoClass2.TuWas(Strings:TStrings);
begin
  Strings.append('2. Demo Klasse');
end;

Procedure TDemoClass3.TuWas(Strings:TStrings);
begin
  strings.append('3. Demo Klasse');
end;

INITIALIZATION
  MyManager.RegisterEntry('Class1',TDemoClass1);
  MyManager.RegisterEntry('Class2',TDemoClass2);
  MyManager.RegisterEntry('Class3',TDemoClass3);

end.
Sobald ich das Programm starte, krachts mit einer Zugriffsverletzung beim RegisterEntry-Aufruf.

Ich vermute das der Aufruf des Klassenkonstruktors erst nach dem abarbeiten der INITIALIZATION-Abschnitte der Units erfolgt. Oder liegt das Problem woanders ?
Angehängte Dateien
Dateityp: zip FactoryDemo.zip (4,9 KB, 8x aufgerufen)
Uwe
e=mc² or energy = milk * coffee²

Geändert von Ghostwalker (29. Apr 2018 um 09:30 Uhr) Grund: Anhang vergessen
  Mit Zitat antworten Zitat
 


Forumregeln

Es ist dir nicht erlaubt, neue Themen zu verfassen.
Es ist dir nicht erlaubt, auf Beiträge zu antworten.
Es ist dir nicht erlaubt, Anhänge hochzuladen.
Es ist dir nicht erlaubt, deine Beiträge zu bearbeiten.

BB-Code ist an.
Smileys sind an.
[IMG] Code ist an.
HTML-Code ist aus.
Trackbacks are an
Pingbacks are an
Refbacks are aus

Gehe zu:

Impressum · AGB · Datenschutz · Nach oben
Alle Zeitangaben in WEZ +1. Es ist jetzt 04:48 Uhr.
Powered by vBulletin® Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz