AGB  ·  Datenschutz  ·  Impressum  







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

class operator OnesComplement ? o.O

Ein Thema von himitsu · begonnen am 18. Nov 2012 · letzter Beitrag vom 14. Mär 2015
Antwort Antwort
Seite 1 von 2  1 2      
Benutzerbild von Stevie
Stevie

Registriert seit: 12. Aug 2003
Ort: Soest
4.042 Beiträge
 
Delphi 10.1 Berlin Enterprise
 
#1

AW: class operator OnesComplement ? o.O

  Alt 2. Mär 2015, 13:41
Bedeutet das ich kann doch den RecordCopy "überladen"?
Naja, als Überladen würd ich das nicht bezeichnen. Da werden System Funktionen gehooked.
D.h. bei allen vom Compiler generierten CopyRecord aufrufen in deiner gesamten Anwendung läuft der extra Dictionary Lookup.

Ich bin ja schon recht großzügig, Code nicht als Hack sondern als "geschickte Ausnutzung der Mechanik" zu bezeichnen, aber das ist definitiv ein Hack - und zwar ein gewaltiger - da muss man schon wissen, was man damit anstellt

Bietet "Deine" Routine da einen Lösung?
Vermutlich denkst du an sowas?

Delphi-Quellcode:
class procedure TFoo.Copy(var dest, source: TFoo);
begin
  dest.a := System.Copy(source.a);
end;
Jo, müsste gehen.

Gibt allerdings noch eine andere Möglichkeit, die genauso funktioniert, wie bei Strings:

Delphi-Quellcode:
type
  TFoo = record
  private
    a: array of string;
    function GetItem(i: Integer): string; inline;
    procedure SetItem(i: Integer; const Value: string); inline;
  public
    property Items[i: Integer]: string read GetItem write SetItem; default;
  end;

function GetArrayRef(A: Pointer): Integer; inline;
type // geliehen aus der System.pas
  PDynArrayRec = ^TDynArrayRec;
  TDynArrayRec = packed record
  {$IFDEF CPUX64}
    _Padding: LongInt;
  {$ENDIF}
    RefCnt: LongInt;
    Length: NativeInt;
  end;
begin
  Result := NativeInt(A);
  if Result <> 0 then
    Result := PDynArrayRec(PByte(A) - SizeOf(TDynArrayRec))^.RefCnt;
end;

function TFoo.GetItem(i: Integer): string;
begin
  Result := a[i];
end;

procedure TFoo.SetItem(i: Integer; const Value: string);
begin
  if GetArrayRef(a) > 1 then
    a := System.Copy(a);
  a[i] := Value;
end;
Stefan
“Simplicity, carried to the extreme, becomes elegance.” Jon Franklin

Delphi Sorcery - DSharp - Spring4D - TestInsight

Geändert von Stevie ( 2. Mär 2015 um 13:59 Uhr)
  Mit Zitat antworten Zitat
Benutzerbild von himitsu
himitsu

Registriert seit: 11. Okt 2003
Ort: Elbflorenz
44.326 Beiträge
 
Delphi 12 Athens
 
#2

AW: class operator OnesComplement ? o.O

  Alt 2. Mär 2015, 14:14
Am schönsten wäre es ja, wenn man auf sowas wie deim GetArrayRef verzichten könnte.
Für Strings hat man das ja inzwischen auch eingebaut. Delphi-Referenz durchsuchenStringRefCount

Copy(arr) ruft System.DynArrayCopy auf, aber du kannst stattdessen, und ohne RefCount vorher zu prüfen, System.DynArrayUnique ausrufen (prüft selbst intern das RefCount)


Aber am "optimalsten" wäre es halt, wenn Emba solche Methoden in der RTTI aufnimmt, also direkt als Flag/Referenz, so wie z.B. beim [Weak]-Status,
und dann in den originalen Funktionen ganz schnell zu schauen, ob es was zum Aufrufen gibt, welches per Class-Operator dort eingetragen wurde.
Ein Therapeut entspricht 1024 Gigapeut.

Geändert von himitsu ( 2. Mär 2015 um 14:18 Uhr)
  Mit Zitat antworten Zitat
Benutzerbild von Mavarik
Mavarik

Registriert seit: 9. Feb 2006
Ort: Stolberg (Rhld)
4.153 Beiträge
 
Delphi 10.3 Rio
 
#3

AW: class operator OnesComplement ? o.O

  Alt 2. Mär 2015, 14:16
Jo, müsste gehen.

Gibt allerdings noch eine andere Möglichkeit, die genauso funktioniert, wie bei Strings:

Delphi-Quellcode:
type
  TFoo = record
  private
    a: array of string;
    function GetItem(i: Integer): string; inline;
    procedure SetItem(i: Integer; const Value: string); inline;
  public
    property Items[i: Integer]: string read GetItem write SetItem; default;
  end;

function GetArrayRef(A: Pointer): Integer; inline;
type // geliehen aus der System.pas
  PDynArrayRec = ^TDynArrayRec;
  TDynArrayRec = packed record
  {$IFDEF CPUX64}
    _Padding: LongInt;
  {$ENDIF}
    RefCnt: LongInt;
    Length: NativeInt;
  end;
begin
  Result := NativeInt(A);
  if Result <> 0 then
    Result := PDynArrayRec(PByte(A) - SizeOf(TDynArrayRec))^.RefCnt;
end;

function TFoo.GetItem(i: Integer): string;
begin
  Result := a[i];
end;

procedure TFoo.SetItem(i: Integer; const Value: string);
begin
  if GetArrayRef(a) > 1 then
    a := System.Copy(a);
  a[i] := Value;
end;
OK Aber dann muss man "überall" den Zugriff ändern.

Ich suche eher eine Lösung für den Umstiegt von Short auf Long und Array[L..H] nach Array of...

Beispiel:

Delphi-Quellcode:
type
  TFooOld = Record
              Bla : Integer;
              Blub : Array[0..10] of Shortstring;
            end;
  TFooNeu = Record
              Bla : Integer;
              Blub : Array of String; // Oder auch TStringDynArray
            end;
Der "Rest" der Software hat keine Ahnung von der Umstellung... Abgesehen von den entsprechenden SetLength.

So ALLE
Delphi-Quellcode:
var
  A,B : TFooNeu;
begin
  ...
  A := B;
end;
müssen sich genau verhalten wie vorher... Ohne
A := B.Clone aufrufen zu müssen....

Mavarik
  Mit Zitat antworten Zitat
Benutzerbild von himitsu
himitsu

Registriert seit: 11. Okt 2003
Ort: Elbflorenz
44.326 Beiträge
 
Delphi 12 Athens
 
#4

AW: class operator OnesComplement ? o.O

  Alt 2. Mär 2015, 14:25
Blub als Array-Property deklarieren und dort im Setter ein UniqueArray.
Ein Therapeut entspricht 1024 Gigapeut.
  Mit Zitat antworten Zitat
Benutzerbild von Stevie
Stevie

Registriert seit: 12. Aug 2003
Ort: Soest
4.042 Beiträge
 
Delphi 10.1 Berlin Enterprise
 
#5

AW: class operator OnesComplement ? o.O

  Alt 2. Mär 2015, 14:28
Blub als Array-Property deklarieren und dort im Setter ein UniqueArray.
Vermutlich müsste er dann alle SetLength auf Blub im Code ändern... - aber die dürften ja über Compilefehler zu finden sein.

Einfach Zähne zusammen beißen, die Record Types vernünftig kapseln und dann is gut.
Stefan
“Simplicity, carried to the extreme, becomes elegance.” Jon Franklin

Delphi Sorcery - DSharp - Spring4D - TestInsight
  Mit Zitat antworten Zitat
Benutzerbild von Mavarik
Mavarik

Registriert seit: 9. Feb 2006
Ort: Stolberg (Rhld)
4.153 Beiträge
 
Delphi 10.3 Rio
 
#6

AW: class operator OnesComplement ? o.O

  Alt 3. Mär 2015, 10:17
Vermutlich müsste er dann alle SetLength auf Blub im Code ändern... - aber die dürften ja über Compilefehler zu finden sein.

Einfach Zähne zusammen beißen, die Record Types vernünftig kapseln und dann is gut.
Leider nicht, da die Software in teilen über 30 Jahre alt ist, sind hier viele Proceduren mit

Procedure Foo(Var Data); und sehr viele "Moves" enthalten.. Da hält der Compiler leider nicht an.
  Mit Zitat antworten Zitat
Benutzerbild von Uwe Raabe
Uwe Raabe

Registriert seit: 20. Jan 2006
Ort: Lübbecke
11.609 Beiträge
 
Delphi 12 Athens
 
#7

AW: class operator OnesComplement ? o.O

  Alt 3. Mär 2015, 10:45
Leider nicht, da die Software in teilen über 30 Jahre alt ist, sind hier viele Proceduren mit

Procedure Foo(Var Data); und sehr viele "Moves" enthalten.. Da hält der Compiler leider nicht an.
Manchmal wirkt ein befreiender Frühjahrsputz Wunder. Alternativ kann man auch jedesmal, wenn man so ein antiquiertes Konstrukt sieht, das vernünftig wegrefaktorisieren. Solche Code-Teile neigen nämlich dazu, den Code im Umfeld mit zu vergiften.
Uwe Raabe
Certified Delphi Master Developer
Embarcadero MVP
Blog: The Art of Delphi Programming
  Mit Zitat antworten Zitat
Benutzerbild von DeddyH
DeddyH

Registriert seit: 17. Sep 2006
Ort: Barchfeld
27.656 Beiträge
 
Delphi 12 Athens
 
#8

AW: class operator OnesComplement ? o.O

  Alt 3. Mär 2015, 10:48
Detlef
"Ich habe Angst vor dem Tag, an dem die Technologie unsere menschlichen Interaktionen übertrumpft. Die Welt wird eine Generation von Idioten bekommen." (Albert Einstein)
Dieser Tag ist längst gekommen
  Mit Zitat antworten Zitat
Benutzerbild von Mavarik
Mavarik

Registriert seit: 9. Feb 2006
Ort: Stolberg (Rhld)
4.153 Beiträge
 
Delphi 10.3 Rio
 
#9

AW: class operator OnesComplement ? o.O

  Alt 3. Mär 2015, 11:16
Manchmal wirkt ein befreiender Frühjahrsputz Wunder. Alternativ kann man auch jedesmal, wenn man so ein antiquiertes Konstrukt sieht, das vernünftig wegrefaktorisieren. Solche Code-Teile neigen nämlich dazu, den Code im Umfeld mit zu vergiften.
Als ich "Antworten" gedrückt habe, dachte ich mir schon das solche Kommentare kommen... Im Prinzip hast Du natürlich Recht...
Ein paar Longstrings in einem Record haben jetzt schon 6 Monate mit nahezu 18/7 Programmierung gekostet... Bei Projekten > 500 Units und > 2 Mio. Zeilen ist nix "mal eben" gemacht. Da gibt es auch keine Inseln die man mal eben umbaut... Jede Änderung zieht sich durch mindestens 350 Units. Immer wenn schon der Grep mehr als 10000 Stellen ausgibt, sucht man nach besseren Lösungen. Besonders, da es 5000 Stellen gibt die weder grep noch der Compiler findet...

Mavarik
  Mit Zitat antworten Zitat
Benutzerbild von Mavarik
Mavarik

Registriert seit: 9. Feb 2006
Ort: Stolberg (Rhld)
4.153 Beiträge
 
Delphi 10.3 Rio
 
#10

AW: class operator OnesComplement ? o.O

  Alt 2. Mär 2015, 14:45
UniqueArray?

Gab es das schon in D2007?
Momentan mach ich immer ein Copy im Setter...
  Mit Zitat antworten Zitat
Antwort Antwort
Seite 1 von 2  1 2      


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 05:41 Uhr.
Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz