Entwickler-Ecke

Delphi Language (Object-Pascal) / CLX - Felder lesen von Datei?


jackie05 - Sa 24.01.09 19:06
Titel: Felder lesen von Datei?
Hallo,
ich hab da mal eine Frage, wie kann ich Felder lesen, die in der Datei sind?

Hier mal mein versuch:

Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
if OpenDialog1.Execute then
begin
  Datei := TFileStream.Create(OpenDialog1.FileName, fmOpenRead);
  for y:=0 to High(Feld) do begin
    for x:=0 to High(Feld) do begin
      Datei.Read(Feld[x,y].Feld, SizeOf(String));
      Datei.Read(Feld[x,y].Feld2, SizeOf(Integer));
      Datei.Read(Feld[x,y].Feld3, SizeOf(Integer));
    end;
  end;
  Datei.Free;
end;


das klappt irgendwie nicht, kann mir vieleicht jemand erklären, wie ich das ambesten machen kann?

Ich bedanke mich schonmal für die Hilfe.

MfG


jackie05 - So 25.01.09 19:12

Hat keiner ne ahnung wie ich meine Felder von Datei lesen kann?
In BlitzMax kann ich so meine Felder laden:

Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
If Not Datei = 0 Then
  For Local xx:Int=0 Until FeldX
    For Local yy:Int=0 Until FeldY
      SpielFeld[xx,yy].Feld = ReadString(Datei,1)
      SpielFeld[xx,yy].SumeXOK = ReadInt(Datei)
      SpielFeld[xx,yy].SumeYOK = ReadInt(Datei)
    Next
  Next
  CloseFile(Datei)
EndIf


nur wie kann ich ReadInt und ReadString in Delphi benutzen?

MfG


Delete - So 25.01.09 19:21

Wenn Du uns mal erklärst, was Du genau mit "Feldern" meinst. Es scheint sich um ein 2-dimensionales Array zu handeln, seh ich das richtig? Und schau Dir Deine verschachtelten Schleifen nochmal genau an, die Laufvariable scheint nicht ganz zu stimmen.


delfiphan - So 25.01.09 19:24

Wie sieht die Datei aus, die du laden willst?


jackie05 - So 25.01.09 19:29

Danke Dir.
Der Code ist von mir in BlitzMax geschrieben, ich wollte nur zeigen, wie ich es meine.
Ich möchte meine Felder in Delphi laden, dazu habe ich ein Typ mit Array verbunden:

Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
type
  TFeld = record
  Wert: integer;
  Feld: string;
  SumeX: integer;
  SumeY: integer;
end;

var
  Form1: TForm1;
  Spielfeld: array[0..11,0..11of TFeld;


und möchte dann die werte die in der Datei stehen, die Felder übergeben.
Beispiel:
Datei.Read(Spielfeld[x,y].Wert,1)
also mit TFileStream, nur weiss ich nicht richtig, wie ich das jetzt anstellen soll.

Edit: So sieht die Datei innen aus:

Delphi-Quelltext
1:
M        M        S       S       M        S       S       M        M        S       N        N        S      N        N        S       M        S      N        N        N        N        N        N        S       N        N        N        N        N        N        N        S       N        N        N        N        N        N        M        M        S       N        N        S       N        N        M                    


Ich hoffe, das man mir weiterhelfen kann.

Danke schonmal.

MfG


jaenicke - So 25.01.09 19:35

Dein Problem ist der String. SizeOf(String) ist immer 4, da es sich nur um einen Pointer handelt.

Der String scheint ja eine Länge von 1 zu haben, nimm doch einfach Char statt String als Typ. ;-)


delfiphan - So 25.01.09 19:35

Und wie soll diese Datei interpretiert werden?
Wert, Feld, SumeX, SumeY - wie sind die in der Datei codiert? Feld scheint wie im Post drüber vermutet ein Char zu sein. Der Rest ist mir jetzt nicht so ganz klar ;)


jackie05 - So 25.01.09 19:44

Wie die Datei Codiert ist, kann ich allerdings nicht genau beschreiben.
Hier mal ein beispiel, wie ich meine Felder in BlitzMax speicher:

Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
Local Datei:TStream = WriteFile("Datei.dat")

If Not Datei = 0 Then
  For Local xx:Int=0 Until FeldX
    For Local yy:Int=0 Until FeldY
      WriteString(Datei, SpielFeld[xx,yy].Feld)
      WriteInt(Datei, SpielFeld[xx,yy].SumeXOK)
      WriteInt(Datei, SpielFeld[xx,yy].SumeYOK)
    Next
  Next
  CloseFile(Datei)
EndIf


Ich weiss, das hier ist kein BlitzMax Forum, es soll ja nur ein beispiel sein, wie ich meine Felder in BlitzMax speicher.

In Delphi müsste es ja so ähnlich funktionieren, wenn ich mich nicht irre.

Edit: Ich habe das so in Delphi versucht:

Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
15:
16:
17:
18:
19:
procedure TForm1.Button4Click(Sender: TObject);
var
  x,y: integer;
  Datei: TFileStream;
begin
  if OpenDialog1.Execute then
  begin
    Datei := TFileStream.Create(OpenDialog1.FileName, fmOpenRead);
              
    for y:=0 to 7 do begin
      for x:=0 to 5 do begin
        Datei.Read(Spielfeld[x,y].Feld, SizeOf(char));
        Datei.Read(Spielfeld[x,y].SumeXOK, SizeOf(integer));
        Datei.Read(Spielfeld[x,y].SumeYOK, SizeOf(integer));
      end;
    end;
    Datei.Free;
  end;
end;


leider klappt das nicht so richtig.

MfG


jaenicke - So 25.01.09 19:47

Da musst du mit dem Debugger durchgehen und schauen wo falsche Werte gelesen werden...


MSCH - So 25.01.09 20:14

Tip: Schreibe keine Strings oder Zahlen ohne Längenangabe in eine Datei.
Wie schon gesagt; strings = Pointer, oder Short-String oder oder oder.

Am besten immer Typ:Länge/Größe:Wert. Das ist dann auch noch kompatible, wenn ich die Datei statt
mit einem Integer mit einen Int64 lesen will

:-)Msch


delfiphan - So 25.01.09 20:16

Für mich sieht es nicht danach aus, als wäre oben in der geposteten Datei irgendwelche Integer codiert, weder Binär noch als Text. Ich kann dir nur raten, ein allgemein bekanntes Format wie XML zu wählen. Das spart dir für die Zukunft Ärger.


jaenicke - So 25.01.09 20:16

user profile iconMSCH hat folgendes geschrieben Zum zitierten Posting springen:
Tip: Schreibe keine Strings oder Zahlen ohne Längenangabe in eine Datei.
Wie schon gesagt; strings = Pointer, oder Short-String oder oder oder.

Am besten immer Typ:Länge/Größe:Wert. Das ist dann auch noch kompatible, wenn ich die Datei statt
mit einem Integer mit einen Int64 lesen will
Da es sich nur um einen Buchstaben handelt ist dies hier gar nicht nötig. Beim Debuggen sollte herauskommen ab wo falsche Werte ankommen. Die Frage ist z.B. ob SumeXOK und SumeYOK wirklich wie ein Delphi-Integer mir 4 Byte gespeichert werden.


delfiphan - So 25.01.09 20:18

Ich sehe zwischen den Buchstaben oben nur 8 Leerzeichen (meistens jedenfalls). Würde darauf hindeuten, dass dort tatsächlich 2 32-bit Integer sind, die im Forum nur nicht korrekt angezeigt werden. Statt Char würde ich AnsiChar schreiben, ansonsten geht es auf Delphi2009 nicht mehr.


MSCH - So 25.01.09 20:20

Theoretisch ja - aber wer sagt, denn das ein Buchstabe nur aus 8 Bit (1 Byte) bestehen muss?
Stichwort: Unicode.
Msch
user profile iconjaenicke hat folgendes geschrieben Zum zitierten Posting springen:
user profile iconMSCH hat folgendes geschrieben Zum zitierten Posting springen:
Tip: Schreibe keine Strings oder Zahlen ohne Längenangabe in eine Datei.
Wie schon gesagt; strings = Pointer, oder Short-String oder oder oder.

Am besten immer Typ:Länge/Größe:Wert. Das ist dann auch noch kompatible, wenn ich die Datei statt
mit einem Integer mit einen Int64 lesen will
Da es sich nur um einen Buchstaben handelt ist dies hier gar nicht nötig. Beim Debuggen sollte herauskommen ab wo falsche Werte ankommen. Die Frage ist z.B. ob SumeXOK und SumeYOK wirklich wie ein Delphi-Integer mir 4 Byte gespeichert werden.