Delphi-PRAXiS

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Sonstige Fragen zu Delphi (https://www.delphipraxis.net/19-sonstige-fragen-zu-delphi/)
-   -   Delphi Boolean killt Variant-Array? (https://www.delphipraxis.net/89805-boolean-killt-variant-array.html)

glkgereon 5. Apr 2007 23:32


Boolean killt Variant-Array?
 
Hi,

Ich möchte zum speichern einiger Konfigurationen ein Array of Variant nehmen.
Diese sind jedoch für jeden Klassentyp (alle von einer Klasse abgeleitet) unterschiedlich...

Dafür habe ich mir folgende Konstruktion überlegt.

Jedoch kommt beim Zuweisen bereits eine Fehlermeldung welche mir sagt dass irgendwas ein "Invalid Variant Type" ist.
Delphi-Quellcode:
  TAgent = class;
  TAgentClass = class of TAgent;
  TConfigEnum = ( ceXMax, ceYMax, ceStdXPos, ceStdYPos, ceStdEnergy, ceRandomInit, ceDeltaEnergy, ceReproduceMin );
  TConfigs = array [TConfigEnum] of array of Variant;

  TClassMap = class
  protected
    FTypeMap: TClassMapArray;
  public
    constructor Create;
    function GetClassID(AC: TAgentClass): Integer; //Get ID for Class
  end;

  TConfig = class
  protected
    FData: TConfigs;
    FClassMap: TClassMap;
  public
    constructor Create;
    destructor Destroy; override;
    procedure SetValue(AC: TAgentClass; CT: TConfigEnum; Value: Variant);
    function GetValue(AC: TAgentClass; CT: TConfigEnum): Variant;
  end;

  TGeneral = class(TAgent);
  TFoodAgent = class(TAgent);
  TAnimalAgent = class(TAgent);

implementation

constructor TClassMap.Create;
var i: Integer;
begin
  inherited;
  FTypeMap[1]:=TGeneral;
  FTypeMap[2]:=TAgent;
  FTypeMap[3]:=TFoodAgent;
  FTypeMap[4]:=TAnimalAgent;
end;

function TClassMap.GetClassID(AC: TAgentClass): Integer;
var i: Integer;
begin
  Result:=-1;
  for i:=Low(FTypeMap) to High(FTypeMap) do
    if FTypeMap[i]=AC then Result:=i;
end;

constructor TConfig.Create;
var i: TConfigEnum;
begin
  inherited;
  FClassMap:=TClassMap.Create;
  for i:=Low(TConfigEnum) to High(TConfigEnum) do
    SetLength(FData[i],cClassCount);
  SetValue(TGeneral,ceXMax,100);
  SetValue(TGeneral,ceYMax,100);
  SetValue(TGeneral,ceRandomInit,True); //<- Hier hakts wohl
  SetValue(TAgent,ceStdXPos,50);
  SetValue(TAgent,ceStdYPos,50);
  SetValue(TFoodAgent,ceStdEnergy,10);
  SetValue(TFoodAgent,ceDeltaEnergy,1);
  SetValue(TFoodAgent,ceReproduceMin,20);
  SetValue(TAnimalAgent,ceStdEnergy,10);
  SetValue(TAnimalAgent,ceDeltaEnergy,-1);
  SetValue(TAnimalAgent,ceReproduceMin,20); //<- Und hier kommt der Error
end;

destructor TConfig.Destroy;
begin
  FClassMap.Free;
  inherited;
end;

procedure TConfig.SetValue(AC: TAgentClass; CT: TConfigEnum; Value: Variant);
begin
  FData[CT][FClassMap.GetClassID(AC)]:=Value;
end;
Zum Zeitpunkt der Zuweisung sieht der FData-Array so aus:
(Aus der Watchlist kopiert und formatiert)
Delphi-Quellcode:
(
  ( //ceXMax
    Unassigned,
    100,
    Unassigned,
    Unassigned
  ),
  ( //ceYMax
    Unassigned,
    100,
    Unassigned,
    Unassigned
  ),
  ( //ceStdXPos
    Unassigned,
    Unassigned,
    50,
    Unassigned
  ),
  ( //ceStdYPos
    Unassigned,
    Unassigned,
    50,
    Unassigned
  ),
  ( //ceStdEnergy
    Unassigned,
    Unassigned,
    Unassigned,
    10
  ),
  ( //ceRandomInit
    Unassigned,
    True,
    Unassigned,
    Unassigned,
    Unknown type: 78,
    Unassigned,
    Unassigned,
    Unassigned,
    Unassigned,
    Unassigned
  ),
  ( //ceDeltaEnergy
    Unassigned,
    Unassigned,
    Unassigned,
    1
  ),
  ( //ceReproduceMin
  )
)
und das kann ich mir nun leider absolut nicht erklären :-(
wieso ist das drittletzte Element zu lang und das letzte so kurz???
Was besagt "Unknown type: 78"?

praktiker 6. Apr 2007 02:13

Re: Boolean killt Variant-Array?
 
Hallo ,
wie man ganz unten in der Watchliste sieht, ist für das letzte Array //ceReproduceMin keine Speicherzuweisung erfolgt.

In dem Abschnitt TConfig.create
solltest du die Zeile
for i:=Low(TConfigEnum) to High(TConfigEnum) do
SetLength(FData[i],cClassCount);
in
for i:=Low(TConfigEnum) to High(TConfigEnum)+1 do
SetLength(FData[i],cClassCount+1);
ändern.

Müsste dann funktionieren.

glkgereon 6. Apr 2007 09:08

Re: Boolean killt Variant-Array?
 
Aua. :wall:
natürlich!

Ich habe es jetzt zwar etwas anders, aber im prinzip das selbe.
Da der dyn.Array von 0 bis 3 und meine Klassen von 1 bis 4 gehen habe ich an der entsprechenden Stellen eine -1 eingefügt...

Delphi-Quellcode:
procedure TConfig.SetValue(AC: TAgentClass; CT: TConfigEnum; Value: Variant);
begin
  FData[CT][FClassMap.GetClassID(AC)-1]:=Value;
end;
Danke für diesen Hinweis :thumb:


Alle Zeitangaben in WEZ +1. Es ist jetzt 14:29 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