Einzelnen Beitrag anzeigen

TiGü

Registriert seit: 6. Apr 2011
Ort: Berlin
3.070 Beiträge
 
Delphi 10.4 Sydney
 
#3

AW: Zugriffsverletzung bei Zeiger auf statisches Array

  Alt 26. Aug 2019, 11:10
Delphi-Quellcode:
unit Codehunter.View;

interface

uses
  Winapi.Windows, Winapi.Messages, System.SysUtils, System.Variants, System.Classes, Vcl.Graphics,
  Vcl.Controls, Vcl.Forms, Vcl.Dialogs, Vcl.StdCtrls;

type
  TForm1 = class(TForm)
    Button1: TButton;
    procedure Button1Click(Sender: TObject);
  private
    { Private declarations }
  public
    { Public declarations }
  end;

  type
  TMyRecord = record
    A: Integer;
    B: Integer;
    C: Byte;
  end;

  TMyRecords = array of TMyRecord;
  PMyRecords = ^TMyRecords;

  TMyClass = class
  private
    FRecords: TMyRecords;
  protected
    function GetRecord(const AIndex: Integer): TMyRecord;
  public
    property Records[const AIndex: Integer]: TMyRecord read GetRecord; default;
  end;

  TMyClassA = class(TMyClass)
  strict private const
    RECS: array[0..1] of TMyRecord = (
      (A: 1; B: 2; C: 3),
      (A: 4; B: 5; C: 6)
    );
  public
    constructor Create;
  end;

  TMyClassB = class(TMyClass)
  strict private const
    RECS: array[0..2] of TMyRecord = (
      (A: 1; B: 2; C: 3),
      (A: 4; B: 5; C: 6),
      (A: 7; B: 8; C: 9)
    );
  public
    constructor Create;
  end;

var
  Form1: TForm1;

implementation

{$R *.dfm}

{ TMyClass }

function TMyClass.GetRecord(const AIndex: Integer): TMyRecord;
begin
  Result := FRecords[AIndex];
end;

{ TMyClassA }

constructor TMyClassA.Create;
var
  I: Integer;
begin
  System.SetLength(FRecords, Length(RECS));
  for I := System.Low(RECS) to System.High(RECS) do
    System.Move(RECS[I], FRecords[I], SizeOf(RECS[I]));
end;

{ TMyClassB }

constructor TMyClassB.Create;
var
  I: Integer;
begin
  System.SetLength(FRecords, Length(RECS));
  for I := System.Low(RECS) to System.High(RECS) do
    System.Move(RECS[I], FRecords[I], SizeOf(RECS[I]));
end;

procedure TForm1.Button1Click(Sender: TObject);
var
  LClassA: TMyClassA;
begin
  LClassA := TMyClassA.Create;
  try
    ShowMessage(LClassA[1].A.ToString);
  finally
    LClassA.Free;
  end;
end;

end.
Aber nur wenn du versprichst, dass TMyRecord keine referenzgezählten Typen verwendet.
Okay sind ordinale Typen (Byte, Integer, Cardinal, Int64). Pfui alles andere (string, Interface, dynamisches Array).
  Mit Zitat antworten Zitat