Delphi-PRAXiS
Seite 1 von 2  1 2      

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Object-Pascal / Delphi-Language (https://www.delphipraxis.net/32-object-pascal-delphi-language/)
-   -   Delphi Statisches array of Single (glFloat) - Exception (https://www.delphipraxis.net/164750-statisches-array-single-glfloat-exception.html)

Flips 28. Nov 2011 15:52

Delphi-Version: 7

Statisches array of Single (glFloat) - Exception
 
Hi,

ich bin gerade ein wenig verwundert, dass folgender Code KEINE Exception wirft:
Delphi-Quellcode:
type glFloat = Single;
[...]
//Lokale Variable
var dummy: array [0..3,0..65535,0..3] of glFloat;
Sobald ich allerdings einen Wert zuweisen will, knallt es mit einer "application-defined exception", deren Code mir Google in einen Stack-Overflow übersetzt ([Edit]Nach kurzer Änderung der Debugger-Einstellungen wirft mir nun auch Delphi direkt ne Stack-Overflow-Exception :stupid: [/Edit]):

Delphi-Quellcode:
var dummy: array [0..3,0..65535,0..3] of glFloat;
begin <- Hier knallt es
  dummy[0,0,0] := 1.0;
[...]
Komischerweise knallt es laut Quelltexteditor direkt bei begin und nicht bei der Zuweisung.

Also wenn ich mal rechne 4 * 65536 * 4 * 4 Byte = ca 4,2 MB....das ist jetzt ja wohl nicht die Welt. Wieso macht mein Delphi 7 da nicht mehr mit?

Bernhard Geyer 28. Nov 2011 15:56

AW: Statisches array of Single (glFloat) - Exception
 
Die so definierten Variablen werden auf den Stack vor beginn deiner Methode/Funktion abgelegt.
Und ich glaube nicht das in deinem Projekte dies maximale Stackgröße auf > 4 MB eingestellt ist.

Flips 28. Nov 2011 15:58

AW: Statisches array of Single (glFloat) - Exception
 
Was wäre denn eleganter, den Stack zu erhöhen (geht ja sicher irgendwie) oder es als globale Variable zu definieren? Ich hab dazu auch schon im Internet was gelesen von wegen "leg es einfach auf dem Heap ab" aber da bin ich nicht so bewandert ;-)

Flips 28. Nov 2011 16:00

AW: Statisches array of Single (glFloat) - Exception
 
https://de.wikibooks.org/wiki/Progra...elphi:_Pointer

Diese Seite erklärt es wunderbar!
Also Danke für den Tipp!

Medium 28. Nov 2011 22:07

AW: Statisches array of Single (glFloat) - Exception
 
Die Floats haben doch bestimmt einen semantischen Zusammenhang mit etwas, was sich gut in einer Klasse kapseln ließe. Felder einer Klasse landen ebenfalls auf dem Heap (statt dem Stack) :)

Flips 29. Nov 2011 08:11

AW: Statisches array of Single (glFloat) - Exception
 
Hm das heißt wenn ich das Array als privates Feld meiner Klasse, in der ich es benutze, deklariere (gekapselt werden muss es nicht, brauch es nur innerhalb der Klasse), dann wird es ebenfalls auf dem Heap abgelegt und ich brauch mich quasi um nichts mehr zu kümmern?

Habe es jetzt so gelöst, dass ich mir folgendes definiert habe:
Delphi-Quellcode:
type THeapArray = array [0..3,0..65535] of Single;
     PHeapArray = ^THeapArray;
Im Zusammenhang mit New und Dispose funktioniert das wunderbar. Wäre aber auch dankbar für eine Alternative ohne New/Dispose.

Blup 29. Nov 2011 09:05

AW: Statisches array of Single (glFloat) - Exception
 
Dann wird das aber etwas komplizierter:
Delphi-Quellcode:
interface

type
  THeapArray = array [0..3,0..65535] of Single;
  PHeapArray = ^THeapArray;

  IHeapArray = interface(IInterface)
    function GetHeapArray: PHeapArray;
    property HeapArray: PHeapArray read GetHeapArray;
  end;

  THeapRecord = record
  private
    FHeapArray: IHeapArray;
    function GetItems: PHeapArray;
  public
    property Items: PHeapArray read GetItems;
  end;

implementation

type
  THeapObject = class(TInterfacedObject, IHeapArray)
  private
    FItems: THeapArray;
  protected
    function GetHeapArray: PHeapArray;
  end;

{ THeapObject }

function THeapObject.GetHeapArray: PHeapArray;
begin
  Result := @FItems;
end;

{ THeapRecord }

function THeapRecord.GetItems: PHeapArray;
begin
  if not Assigned(FHeapArray) then
    FHeapArray := THeapObject.Create;

  Result := FHeapArray.HeapArray;
end;
Delphi-Quellcode:
procedure TForm1.ButtonTestClick(Sender: TObject);
var
  MyRecord: THeapRecord;
begin
  MyRecord.Items[2, 65000] := 1.456;

  ShowMessage(Format('Wert: %f', [MyRecord.Items[2, 65000]]));
end;

UliBru 29. Nov 2011 09:09

AW: Statisches array of Single (glFloat) - Exception
 
wie wäre es denn mit

Delphi-Quellcode:
type TMeinArray = array of array of array of single;


und dann später

Delphi-Quellcode:
//local
var dummy: TMeinArray;
begin
  SetLength(dummy,4,65536,4);
Edit: oops, sorry, hier ging es ja um statische Arrays

Flips 29. Nov 2011 10:01

AW: Statisches array of Single (glFloat) - Exception
 
@Blup:

Wieso so kompliziert? Also ich habe grad keine Möglichkeit es zu testen, aber sollte - sofern die Aussage, Klassenvariablen werden auf dem Heap abgelegt, stimmt - folgende Methode nicht funktionieren?
Delphi-Quellcode:
type THeapArray = array[0..65535,0..3] of Single;

type
  TMyClass = class
  private
    FHeapArray : THeapArray;
end;
@UliBru
Später könnte/sollte es dynamisch werden. Habe gerade mal das Web befragt und folgende Seite gefunden: Arrays in Object Pascal
Hier steht die Antwort, dynamische Arrays ("Delphi's dynamische Arrays") werden im Heap angelegt.

----

Da ich sowieso später dynamisch werden will nehm ich am besten direkt ein dynamisches Array. Habe ich da eigentlich Performanceeinbußen gegenüber statischen Arrays?
Da habe ich nur folgendes Zitat gefunden über einen Testcode statisch vs dynamisch:
Zitat:

This program shows that while allocating/decallocating a dynamic array (especially mult-dimensional dynamic arrays) isn't free, but access to a dynamic array can be faster than a static array!
Wenn dem so wäre, dann wäre das ja ein gewaltiges pro für den Einsatz eines dynamischen Arrays. Zumal ich die Größe sowieso nur einmal Abhängig von einer Nutzereingabe einstellen will und dann nie wieder. Somit scheiden Performanceeinbußen wegen SetLength schonmal aus.

Blup 29. Nov 2011 10:10

AW: Statisches array of Single (glFloat) - Exception
 
Zitat:

@Blup:

Wieso so kompliziert? Also ich habe grad keine Möglichkeit es zu testen, aber sollte - sofern die Aussage, Klassenvariablen werden auf dem Heap abgelegt, stimmt - folgende Methode nicht funktionieren?
Die Fragestellung war, wie kann man das machen ohne GetMem und FreeMem und natürlich auch ohne einen Konstruktor oder Destruktor bei der Verwendung aufrufen zu müssen.

Edit:
Und dynamische Arrays mit SetLength() natürlich auch nicht, sonst würde die ursprünglich Fragestellung keinen Sinn machen.


Alle Zeitangaben in WEZ +1. Es ist jetzt 05:18 Uhr.
Seite 1 von 2  1 2      

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