Delphi-PRAXiS

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Sonstige Fragen zu Delphi (https://www.delphipraxis.net/19-sonstige-fragen-zu-delphi/)
-   -   Delphi set of.. speichern/laden? (https://www.delphipraxis.net/75745-set-speichern-laden.html)

Angel4585 24. Aug 2006 12:03


set of.. speichern/laden?
 
Hallo,

ich habe folgendes:
Delphi-Quellcode:
type
  TMyTyp = (mt1,mt2,mt3,mt4,mt5);
  TMyTypes = set of TMyTyp;

.
.

procedure SaveToFile(ATyp : TMyTypes);
begin
//Was muss hier rein?
end;

procedure Test;
var mytyp : TMyTypes;
begin
mytyp := [mt1,mt2,mt4];
SaveToFile(mytyp);
end;
Wie muss die Prozedur SaveToFile aussehen, damit ich später ein möglichst einfaches LoadFromFile machen kann?

ich hatte mal irgendwo das Phänomen, dass solche sets als Integer abgespeichert wurden. Dabei hatte der erste Wert den Wert "1", der zweite den Wert "2", der dritte "4", der vierte "8", diese dann alle zusammenaddiert wurden und somit eindeutig in einer Zahl den Inhalt des gespeicherten Sets dargestellt haben.
//Edit: In diesem Fall wäre das die Zahl "11" die diese zusammensetzung eindeutig darstellt und die nicht anders zusammenzusetzen ist.

Gibt es dafür einen Befehl der das macht?

Hoffentlich hab ich mich verständlich ausgedürckt :oops:

MfG :angel:

Khabarakh 24. Aug 2006 12:08

Re: set of.. speichern/laden?
 
Kleiner Tipp:
Hier im Forum suchenSet speichern
;)

3_of_8 24. Aug 2006 12:11

Re: set of.. speichern/laden?
 
Ein Set ist ein Bitvektor.

Das sieht dann bei 5 Werten etwa so aus:

00000000 00000000 00000000 000abcde

Wenn a im set ist, dann ist in dem Bitvektor a=1, ansonsten a=0. Bei b-e ist das dann analog.

Wenn du also ein Set speichern/laden willst, musst du es beim Speichern nur nach Integer casten und dann abspeichern, beim Laden nen Integer laden und in deinen Settyp casten.

Angel4585 24. Aug 2006 12:20

Re: set of.. speichern/laden?
 
wie genau sprech ich jetzt die Bits an?


also wenn ich a,b,c,d,e hab stehen die 00000000 00000000 00000000 000edcba drin.

also wenn die Bits ein string wären wäre es
Delphi-Quellcode:
bits[Length(bits)-Ord(a)]
wo ich setzen müsste für a.
aber wie bekomm ich die als Bits? oder soll ich die besser quadrieren?

Also
Delphi-Quellcode:
zahl:=zahl+Round(power(Ord(a)+1,2));
wenn es das schon gäbe, als einfach Funktion oder so die das komplette Set gleich speichert wäre das viel einfacher...

ok, das speichern hab ich:

Delphi-Quellcode:
function GetZahl(ASet : TMyTypes):Integer;
var i : integer;
begin
if TMyTyp(0) in ASet then
  Result:=1
else result:=0;
for i:= 1 to 4 do//Kann man die Anzahl der Werte dynamisch ermitteln?
  if TMyTyp(i) in ASet then
    Result:=Result+Round(power(i,2));
end;
aber wie lade ich das jetzt wenn ich z.B. "11" bekomme?

3_of_8 24. Aug 2006 12:43

Re: set of.. speichern/laden?
 
Wenn du ein Set in einen Integer umwandeln willst, dann caste es einfach nach integer und vice versa.

Angel4585 24. Aug 2006 12:49

Re: set of.. speichern/laden?
 
Delphi-Quellcode:
Integer(myset);
ergibt aber ne fehlerhafte Typenumwandlung

die Schleife hab ich jetz folgendermaßen überarbeitet:

Delphi-Quellcode:
  function GetZahl(ASet : TMyTypes):Integer;
  var mytest : TMyTyp;
  begin
  Result:=0;
  for mytest in ASet do
    if Ord(mytest) = 0 then
      Result:=Result+1
    else Result:=Result+Round(Power(Ord(mytest),2));
  end;
aber das mit dem Laden... das will irgendwie nicht...

Khabarakh 24. Aug 2006 13:08

Re: set of.. speichern/laden?
 
Zitat:

Zitat von 3_of_8
Wenn du also ein Set speichern/laden willst, musst du es beim Speichern nur nach Integer casten [...]

Und wenn das Set mal größer als 32 Bit ist, schaust du in die Röhre. Toll.

Angel4585 24. Aug 2006 13:12

Re: set of.. speichern/laden?
 
Also beim laden bin ich jetzt soweit, aber häng an der entscheidenden Stelle:

Delphi-Quellcode:
  function GetSet(AZahl : integer):TMyTypes;
  var
    mytest : TMyTyp;
    cnt,i,lzahl : integer;

  begin
  cnt:=0;
  repeat
  inc(cnt);
  until Round(Power(cnt,2))> AZahl;

  lzahl:=AZahl;
  Result:=[];
  for i:= Pred(cnt) downto 1 do
    if Round(Power(i,2)) <= lZahl then
      begin
      lzahl:=lzahl-Round(Power(i,2));
      Result:= (Result or TMyTyp(i));
      end;
  if lzahl = 1 then
    Result:= Result or TMyTyp(0);
  end;
ich habe eben das Result und möchte einen Teil davon setzen. wie mache ich das?
OR und + gehen beide nicht. Muss was anderes her?

Reinhold 24. Aug 2006 13:19

Re: set of.. speichern/laden?
 
Wie wärs mit: ein Set Datentyp speichern

bernau 24. Aug 2006 13:38

Re: set of.. speichern/laden?
 
Ein Typecasting auf ein Set zum Speichern halte ich für ziemlich gefährlich.

1) Wie Khabarakh sagte, kann ein Set auch mal größer 32Bit sein.

2) Ein Set kann(muss) auch, mal erweitert werden, wenn's notwendig ist. Was bekommt man denn da heraus, wenn man eine alte Setstruktur läd.

Ich würde mir da eher eine Get bzw. Set-Procedure schreiben

z.B.

Delphi-Quellcode:
Function MySetToString(aSet:TMySet):String;
Function StringToMySet(aString:String):TMySet;
Da hast du dann die richtige Kontrolle.

Angel4585 24. Aug 2006 13:41

Re: set of.. speichern/laden?
 
und was soll in den Strings stehen? "001001101101" oder sowas? und die dann durchlaufen?

bleibt immernoch die Frage:
Delphi-Quellcode:
Result:= (Result or TMyTyp(i));//Wie geht das richtig?
ich bekomms nich hin :(

bernau 24. Aug 2006 13:46

Re: set of.. speichern/laden?
 
Zitat:

Zitat von Angel4585
und was soll in den Strings stehen? "001001101101" oder sowas? und die dann durchlaufen?

Ja.

Du kannst natürlich auch einen anderen Typ als String verwenden. Aber durch die Set/Get-Procedure kontrollierst du, wie gespeichert wird. Und wenn das Set mal erweitert wird, hast du keine Probleme beim Speichern bzw. lesen.


Gerd

himitsu 24. Aug 2006 14:02

Re: set of.. speichern/laden?
 
Wieso sollte ein set geneu einem Integer entsprechen ... bei 5 Werten ist es ein Byte :warn:

Wenn man also einen SET konvertieren will, sollte man auch die größe beachten.
Also entweder weiß man die, oder man guckt einfach ma mit SizeOf nach.
Und wenn dann die Größe bekannt ist, dann einfach nur noch den passenden Typen aussuchen ... wenn keine Passender existiert, dann kann man sich immernoch mit 'nem Array, oder 'nem Record passender Größe behelfen ^^

Sidorion 24. Aug 2006 14:09

Re: set of.. speichern/laden?
 
Wenn Dein Set Published ist, dann kannst Du Dir mit der Unit TypeInfo behelfen. da gibts Methoden, um Sets in Strings zu wandeln und umgekehrt.

Angel4585 24. Aug 2006 14:29

Re: set of.. speichern/laden?
 
Das ist ja alles schön und gut... aber:

Zitat:

Zitat von Angel4585
bleibt immernoch die Frage:
Delphi-Quellcode:
Result:= (Result or TMyTyp(i));//Wie geht das richtig?

:roll:

BTW: Das Set hat nicht mehr als 32 Werte .. vllt so um die 20. Die Zahl soll an ein php-Skript geschickt werden und in eine MySQL-Datenbank fließen. Danach muss ich diese Zahl wieder mit dem Skript auslesen und im programm auswerten. Ein String oder eine Zahl wäre also am geeignetsten.

himitsu 24. Aug 2006 15:43

Re: set of.. speichern/laden?
 
20 ... aufgerundet auf die nächste Bytegrenze ergibt das also 24 = 3 Byte


theoretisch gibt es also keinen nativen Typen für eine direkte Umwandlung

Du könntest es aber mit solchen Typen versuchen.
Delphi-Quellcode:
Type TTripple = packed Array[0..2] of Byte;

Type TIrgendwas = packed Record
    Lo: Word;
    Hi: Byte;
  End;

bernau 24. Aug 2006 15:48

Re: set of.. speichern/laden?
 
Zitat:

Zitat von Angel4585
bleibt immernoch die Frage:
Delphi-Quellcode:
Result:= (Result or TMyTyp(i));//Wie geht das richtig?


Probier mal folgendes:

Delphi-Quellcode:
result:=result + [TMyTyp(i)];




Gerd[delphi]


Alle Zeitangaben in WEZ +1. Es ist jetzt 05:45 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-2025 by Thomas Breitkreuz