AGB  ·  Datenschutz  ·  Impressum  







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

Property via AsString;AsInteger;AsBoolean;.. laden

Ein Thema von -=ZGD=- · begonnen am 23. Aug 2012 · letzter Beitrag vom 24. Aug 2012
Antwort Antwort
Seite 3 von 4     123 4      
Iwo Asnet

Registriert seit: 11. Jun 2011
313 Beiträge
 
#21

AW: Property via AsString;AsInteger;AsBoolean;.. laden

  Alt 23. Aug 2012, 13:14
Wir arbeiten hier seit Jahren mit dem Vorschlag von Thom (Variants).

Unsere Lösung ist so banal, das wir auf Typensicherheit, OOP, CleanCode usw. an der Stelle verzichten. Die Unit ist 186 Zeilen lang und implementiert einen bösen Singleton namens 'Setup'. Fertig.

Wir verwenden die Eigenschaften 'AsInteger', 'AsString', 'AsBoolean', um komfortabler auf Daten zugreifen zu können (nötig ist das nicht):

Delphi-Quellcode:
ValueAsVariant := Setup['MySetting'];
ValueAsInteger := Setup.AsInteger['MyIntegerSetting'];
ValueAsBoolean := Setup.AsBoolean['MyBooleanSetting'];
...
Wir hatten bisher nie die Muße, über den Sinn zu diskutieren. Die Unit wurde in 30 min zusammengebaut und funktioniert.

Nein, und unsere Anwendungen haben keine 1000 Einstellungen. Höchstens 20.

Wer mit Metadaten arbeitet (und hier haben wir welche), sollte sich mit den Variants vertraut machen.
  Mit Zitat antworten Zitat
-=ZGD=-

Registriert seit: 25. Apr 2006
Ort: Bad Aibling
105 Beiträge
 
Delphi 10.1 Berlin Professional
 
#22

AW: Property via AsString;AsInteger;AsBoolean;.. laden

  Alt 23. Aug 2012, 13:18
Wir arbeiten hier seit Jahren mit dem Vorschlag von Thom (Variants).

Unsere Lösung ist so banal, das wir auf Typensicherheit, OOP, CleanCode usw. an der Stelle verzichten. Die Unit ist 186 Zeilen lang und implementiert einen bösen Singleton namens 'Setup'. Fertig.

Wir verwenden die Eigenschaften 'AsInteger', 'AsString', 'AsBoolean', um komfortabler auf Daten zugreifen zu können (nötig ist das nicht):

Delphi-Quellcode:
ValueAsVariant := Setup['MySetting'];
ValueAsInteger := Setup.AsInteger['MyIntegerSetting'];
ValueAsBoolean := Setup.AsBoolean['MyBooleanSetting'];
...
Wir hatten bisher nie die Muße, über den Sinn zu diskutieren. Die Unit wurde in 30 min zusammengebaut und funktioniert.

Nein, und unsere Anwendungen haben keine 1000 Einstellungen. Höchstens 20.

Wer mit Metadaten arbeitet (und hier haben wir welche), sollte sich mit den Variants vertraut machen.
Meine Worte
Bei mir werden es auch nicht mehr als 50 Werte werden.

Ich finde diese Lösung eben einfach und alltagstauglich. Man muss nicht alles auf die Spitze treiben.

@Shark: Ich habe doch einen Setter im Record..wo finde ich meinen Fehler?
Stefan Michalk
  Mit Zitat antworten Zitat
Benutzerbild von s.h.a.r.k
s.h.a.r.k

Registriert seit: 26. Mai 2004
3.159 Beiträge
 
#23

AW: Property via AsString;AsInteger;AsBoolean;.. laden

  Alt 23. Aug 2012, 13:48
@Shark: Ich habe doch einen Setter im Record..wo finde ich meinen Fehler?
Jo, habe übersehen, dass es sich um eine reine write-Property bei Value handelt. Sowas gibts bei mir nie, daher ging von einem read aus

So, die Doku muss der Entwickler sowieso bei sich haben, damit er weiß, welche Konfigurationfelder er eigentlich hat, da ist´s egal, dass er noch schaut und liest: Typ.INTEGER.
Guter Code benötigt (fast) keine Doku. Ich persönlich finde es praktischer, wenn mir IntelliSense sagt, welche Optionen ich denn zur Auswahl habe, anstatt in der Doku nachschauen zu müssen. Dann kann ich alles an Ort und Stelle auswählen nud sehe auch beim Compilieren, ob es knallt, wenn Änderungen an der Configuration-Klasse vorgenommen werden.

Folgendes Beispiel:
Delphi-Quellcode:
Port := Config.GetValue('port').AsInteger;
Port := Config.GetValue('Port').AsInteger;
// Was von den beiden ist richtig? Klar, man könnte in der GetValue()
// Methode noch auf Lower- oder UpperCase umwandeln, aber es kann
// hier leicht knallen.

// Wenn ich aber nun folgendes habe, erscheint in meinem Code eine
// Auflistung aller optionen, die die Klasse Config anbietet. Grob
// mal mit IntelliSense skizziert :)
Port := Config.+----------------+
               | MySQL |
               | Printer |
               | UserSpecific |
               +----------------+

// Klar, muss die Configuration-Klasse entsprechend angepasst werden,
// sodass die Auswahl kommt. Aber so kann der Programmierer sich sehr
// leicht "durchhangeln", bis er das hat, was er sucht:
Port := Config.MySQL.Port;
Davon losgelöst kann man eben auch bzgl. den Variants argumentieren, was ich schon habe. Wer aber die Variants-Lösung bevorzugt, dem sei gesagt, dass ich nichts dagegen habe. Ich beschreibe hier nur den Weg, den ich bevorzugen würde -- aus besagten Gründen

Zitat:
Das alles sein Für und Wider hat, dagegen ist nichts einzuwenden. Letztlich entscheidet das Gutdünken des Entwicklers darüber, wie er es lösen möchte.
Was anderes habe ich nie behauptet Viele Wege führen ans Ziel...
»Remember, the future maintainer is the person you should be writing code for, not the compiler.« (Nick Hodges)
  Mit Zitat antworten Zitat
bepe

Registriert seit: 17. Okt 2006
119 Beiträge
 
#24

AW: Property via AsString;AsInteger;AsBoolean;.. laden

  Alt 23. Aug 2012, 13:50
Delphi-Quellcode:
type
  RConfig2 = record
  private
    fKey: String;
    fValue: Variant;
    function GetAsString: String;
    function GetAsInteger: Integer;
  public
    property Key: String read fKey write fKey;
    property Value: Variant write fValue;
    property AsString: String read GetAsString;
    property AsInteger: Integer read GetAsInteger;
  end;
Ich würde im Record die Setter Methoden einfügen, nicht in der Config Klasse. Dann kannst du einfach ...AsInteger := 4711 tippen, anstatt ein Record übergeben zu müssen.

Delphi-Quellcode:
type
  TConfig = class(TObject)
  private
    ...
    fList: TConfigList;
    fList2: TConfigList2;

    ...
    function GetVariantValue(aID: String): RConfig2;
    procedure SetVariantValue(aID: string; aValue: Variant);

    ...
  public
    constructor create;

    ...
    property Item[aKey: String]: RConfig2 read GetVariantValue write SetVariantValue;
    ...
  end;
Hier ist der Getter ausreichend. Aber wenn schon ein Setter da ist, dann definitiv mit RConfig2 arbeiten nicht mit Variant. Auch wenn ich nichts gegen Variant habe (doch eigentlich schon ), es macht hier einfach keinen Sinn.

mfg,
bp
  Mit Zitat antworten Zitat
Benutzerbild von s.h.a.r.k
s.h.a.r.k

Registriert seit: 26. Mai 2004
3.159 Beiträge
 
#25

AW: Property via AsString;AsInteger;AsBoolean;.. laden

  Alt 23. Aug 2012, 14:00
Wenn du den Implicit-Operator überladen würdest, solltest du deine Setter-Methode so belassen können, wie du es hast. Mal schnell aus dem Kopf heraus aufgeschrieben:
Delphi-Quellcode:
TBlub = class
private
  FRec : TMyRecord;
  procedure SetRec(Value: TMyRecord);
public
  property Rec : TMyRecord read FRec write SetRec;
end;

procedure TBlub.SetRec(Value: TMyRecord);
begin
  FRec := Value;
end;


TMyRecord = class
private
  FValue : Integer;
public
  operator Implicit(Value: Integer): TMyRecord;
  property Value : Integer read FVaule;
end;

TMyRecord.Implicit(Value: Integer): TMyRecord;
begin
  Result.FValue := Value;
end;
»Remember, the future maintainer is the person you should be writing code for, not the compiler.« (Nick Hodges)
  Mit Zitat antworten Zitat
Iwo Asnet

Registriert seit: 11. Jun 2011
313 Beiträge
 
#26

AW: Property via AsString;AsInteger;AsBoolean;.. laden

  Alt 23. Aug 2012, 14:03
Guter Code benötigt (fast) keine Doku.
Korrekt, aber das ist mit dem hier vorliegenden Problem (Zugriff über Metainformation, hier: Eigenschaftsnamen) nicht zu lösen.

Wir können das ganz einfach durch einen applikationsspezifischen Wrapper hinbekommen:

Delphi-Quellcode:
Type
  TSpecificConfig = Class
  Public
    Property MyInteger : Integer Read GetMyInteger Write SetMyInteger;
  End;

...
Function TSpecificConfig.GetMyInteger : Integer;
Begin
  Result := VarToInt (Item['MyInteger']);
End;
Dies lässt sich noch vereinfachen, indem die Konfigurationsnamen in einem konstanten Array vorgehalten werden und es pro Datentyp einen IndexGetter und -setter gibt, also z.B. so:

Delphi-Quellcode:
Type
  TSpecificConfig = Class
    Const Values : Array [0..xx] of String = ('MyInt', 'MyString'...);
  Public
    Property MyInt : Integer index 0 Read GetInteger Write SetInteger;
    Property MyString : String index 1 Read GetString Write SetString;
  End;

...
Function TSpecificConfig.GeInteger (Index : Integer) : Integer;
Begin
  Result := VarToInt (Item[Values[Index]]);
End;
Der Zugriff erfolgt dann über eine Instanz der 'TSpecific'-Klasse.

Wie gesagt: Wer's toll findet, kann sich die Mühe machen.

Mir reicht:
Setup['MyInt'] := 4711;
  Mit Zitat antworten Zitat
-=ZGD=-

Registriert seit: 25. Apr 2006
Ort: Bad Aibling
105 Beiträge
 
Delphi 10.1 Berlin Professional
 
#27

AW: Property via AsString;AsInteger;AsBoolean;.. laden

  Alt 23. Aug 2012, 15:56
Delphi-Quellcode:
type
  RConfig2 = record
  private
    fKey: String;
    fValue: Variant;
    function GetAsString: String;
    function GetAsInteger: Integer;
  public
    property Key: String read fKey write fKey;
    property Value: Variant write fValue;
    property AsString: String read GetAsString;
    property AsInteger: Integer read GetAsInteger;
  end;
Ich würde im Record die Setter Methoden einfügen, nicht in der Config Klasse. Dann kannst du einfach ...AsInteger := 4711 tippen, anstatt ein Record übergeben zu müssen.

Delphi-Quellcode:
type
  TConfig = class(TObject)
  private
    ...
    fList: TConfigList;
    fList2: TConfigList2;

    ...
    function GetVariantValue(aID: String): RConfig2;
    procedure SetVariantValue(aID: string; aValue: Variant);

    ...
  public
    constructor create;

    ...
    property Item[aKey: String]: RConfig2 read GetVariantValue write SetVariantValue;
    ...
  end;
Hier ist der Getter ausreichend. Aber wenn schon ein Setter da ist, dann definitiv mit RConfig2 arbeiten nicht mit Variant. Auch wenn ich nichts gegen Variant habe (doch eigentlich schon ), es macht hier einfach keinen Sinn.
Ich würde mich jetzt für die Variante mit Setter im Record entscheiden.
Die ist drin und sollte auch funktionieren...sollte.

Ich debugge.

Was passiert bei der jetzigen Konstellation:

Delphi-Quellcode:
type
  RConfig2 = record
  private
    fKey: String;
    fValue: Variant;
    function GetAsString: String;
    function GetAsInteger: Integer;
    procedure SetAValue(aValue: Variant);
  public
    property Key: String read fKey write fKey;
    property Value: Variant read fValue write fValue;
    property AsString: String read GetAsString;
    property AsInteger: Integer read GetAsInteger;
  end;
und property Item[aKey: String]: RConfig2 read GetVariantValue; Ich strebe an, über
Code:
.Value:= ?
die Wertzuweisung zu machen.

Jedoch läuft er beim Aufruf von myConfig.Item['dbconfig'].Value:= 2312 immer in GetVariantValue was mir auch logisch erscheint.
Nur wie bringe ich diesen Zugriff so hin, dass es nach meinem Wunsch funktioniert?
Stefan Michalk
  Mit Zitat antworten Zitat
Benutzerbild von s.h.a.r.k
s.h.a.r.k

Registriert seit: 26. Mai 2004
3.159 Beiträge
 
#28

AW: Property via AsString;AsInteger;AsBoolean;.. laden

  Alt 23. Aug 2012, 16:01
Du willst doch, dass es einfach funktioniert. Warum nimmst du dann nicht einfach das was ich geschrieben habe? Das was ich geschrieben habe, funktioniert nicht mal, da dann die Variable Key nicht mit übernommen wird. Shit...
»Remember, the future maintainer is the person you should be writing code for, not the compiler.« (Nick Hodges)

Geändert von s.h.a.r.k (23. Aug 2012 um 16:17 Uhr)
  Mit Zitat antworten Zitat
-=ZGD=-

Registriert seit: 25. Apr 2006
Ort: Bad Aibling
105 Beiträge
 
Delphi 10.1 Berlin Professional
 
#29

AW: Property via AsString;AsInteger;AsBoolean;.. laden

  Alt 23. Aug 2012, 16:11
Du willst doch, dass es einfach funktioniert. Warum nimmst du dann nicht einfach das was ich geschrieben habe?
Dann muss ich wieder so viel umbauen...

Und ich muss so ehrlich sein und sagen, dass mir die Einarbeitungszeit in Implicit für diese Miniklasse als zu hoch erscheint.

Es sieht so aus, als ist meine Vorstellung in dieser Art auf meiner Codebasis doch nicht so ohne Weiteres umzusetzen...

Ich bekomme einfach diese
Code:
Inkompatible Typen
Warnung nicht weg.

Vor allem frage ich mich, wie es funktionieren soll, wenn der Setter rein im Record deklariert ist..
Stefan Michalk
  Mit Zitat antworten Zitat
Benutzerbild von s.h.a.r.k
s.h.a.r.k

Registriert seit: 26. Mai 2004
3.159 Beiträge
 
#30

AW: Property via AsString;AsInteger;AsBoolean;.. laden

  Alt 23. Aug 2012, 16:25
Dann muss ich wieder so viel umbauen...
Viel wäre es ja nicht gewesen, sondern nur ein paar Zeilen. Nur leider hatte die Idee das gleiche Problem, wie du es im Moment hast.

Quick and Dirty könntest es so umbauen, dass du den folgenden Aufruf hast:
myConfig.Item['dbconfig'] := myConfig.Item['dbconfig'].SetValue(2312); Schön ist aber was anders...

Würde dann eher vorschlagen, dass du der TConfig eine SetItemValue(Name: string; Value: Variant) Methode spendierst.

Oder eine ganz andere Alternative wäre es einen Zeiger auf den Record zurückzugeben, also bei GetVariantValue eien PRConfig2. Aber ob das so toll wäre...
»Remember, the future maintainer is the person you should be writing code for, not the compiler.« (Nick Hodges)
  Mit Zitat antworten Zitat
Antwort Antwort
Seite 3 von 4     123 4      


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 00:50 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