Entwickler-Ecke

Sonstiges (Delphi) - nach string in einer datei suchen und die strings danach


ASMJmper - Di 06.10.09 13:07
Titel: nach string in einer datei suchen und die strings danach
moin

und zwar hab ich mal bisschen angefangen mich mit delhpi zu beschäftigen nu hab ich gleich mal mein erstes prob was ich einfach nicht wirklich in den griff bekomme :-(

so hier zu meinem vorhaben

ich lade meine datei in eine Tsringlist

Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
15:
16:
procedure TForm1.Button1Click(Sender: TObject);
var stringliste : Tstringlist;
    index,
    start,ende   : integer;
begin
stringliste := TStringList.Create;
stringliste.LoadFromFile(c:\testdatei.txt);
for index := 0 to stringliste.Count - 1 do
begin
if pos('Information:', stringliste.strings[index]) >0  then   //nach string suchen
begin
  start := pos('[',stringliste.Strings[index]);
  ende  := Pos(']',Copy(stringliste.Strings[index],start,length(stringliste.Strings[index])));
  Memo2.Lines.Add(copy(stringliste.Strings[index],start,ende));
end;
end;

der inhalt der datei sieht so aus
Zitat:

haufen text der mich nicht interessiert ^^

Information:
[CPU: 3300]
[RAM: 4000]
[Win: Win2k]
usw.


ich glaub in der if abfrage liegt der fehler weil es wird nichts in der memo komp geadded :-(
wie gesagt ich möchte die strings nach Information: in die memo komp schreiben hoffe ihr könnt mir helfen

danke

asm


thepaine91 - Di 06.10.09 13:19

Ja ich sehe schon mal ein Fehler

Wenn du Copy(*,Start,Ende) machst.
Copy(*,Index,Count) Du sagst starte bei Start und die Länge ist bis zur Position von Ende.

So ist es aber länger als du es willst jetzt solltest du diesen Fehler schonmal finden.

Edit: Wenn das wirklich so aufgebaut ist:
information:
bla
bla
bla

Dann ist klar das er in der Zeile in der er Information findet keine '[' mehr findet.


Wo kommt das Memo2.Lines.Add(copy(stringliste.Strings[b],start,ende)); her?


ASMJmper - Di 06.10.09 13:35

also der code läuft so halb wie er oben steht ich muss nur index +1 setzen dann gibt er mir schon mal die cpu aus
mmmhhhh


Lannes - Di 06.10.09 15:01

Hallo,

@user profile iconthepaine91:
Strings[] ist das Default-Property der TStringList, das kann man angeben, kann es aber auch weglassen.

user profile iconASMJmper hat folgendes geschrieben Zum zitierten Posting springen:
also der code läuft so halb wie er oben steht ich muss nur index +1 setzen dann gibt er mir schon mal die cpu aus
mmmhhhh
das ist klar, denn die If-Bedingung prüft auf 'Information:', wird das gefunden, steht in Index+1 "cpu" und nicht in Index, denn dort steht doch "Information". :wink:
Und das die anderen nicht gefunden werden ist auch klar, denn vor den weiteren Einträgen seht eben nicht "Informationen".

Ich würde für die Interpretation der Daten While-Schleifen einsetzen,
Pseudocode:
- solange 'Information:' nicht enthalten ist, gehe weiter
- 'Information:' gefunden, erhöhe Index + 1
- solange Stop-Bedingung nicht erreicht, werte Einträge aus

oder mit IndexOf arbeiten.


Noch einige Anmerkungen:
- try-finally-Anweisung mit Freigabe der TStringList fehlt
- ein zwischenspeichern von "stringliste.Strings[index]" in einer Variable verbessern die Performance des Codes


thepaine91 - Di 06.10.09 17:29

Lannes was hat das mit mir zu tun hab Strings[] nie angezweifelt :O

---Moderiert von user profile iconNarses: Beiträge zusammengefasst---

asm jumper du hast nicht gelesen was ich geschrieben habe oder?

Da hab ich das problem mit dem Index und leer strings schon behandelt :O ich gebs auf ^^ ich geh inaktiv....


Lannes - Mi 07.10.09 00:01

Hallo,


user profile iconthepaine91 hat folgendes geschrieben Zum zitierten Posting springen:
Lannes was hat das mit mir zu tun hab Strings[] nie angezweifelt :O


habe die Zeile aus Deinem Beitrag als Frage bzgl. Strings[] interpretiert: :wink:
user profile iconthepaine91 hat folgendes geschrieben Zum zitierten Posting springen:

Wo kommt das Memo2.Lines.Add(copy(stringliste.Strings[b],start,ende)); her?


SmileySN - Mi 07.10.09 00:11

Wenn in der Datei unter "Information:" immer 3 Zeilen stehen die man einlesen möchte, dann kann man das ja auch auf die primitive Art machen und die 3 Zeilen im If Statement einfach noch zweimal schreiben, dann den ersten Block mit Index+1, den zweiten Block mit Index+2 den dritten Block mit Index+3.
Danach hat man alle 3 Werte in der Memo stehen.
Damit sieht man erst mal, dass es so funktioniert und versteht wie es geht.
Dann baut man, stattdessen, eine Schleife in das If Statement ein, die alle Werte ausliest bis zu einem Endpunkt.


ASMJmper - Mi 07.10.09 09:30

Lannes kannste deinen Pseudocode mal in einen code für delphi beginner schreiben :)
sry wie gesagt hab erst vor kurzem mit delphi angefangen wär dir dankbar

@SmileySN
könnte man machen aber lannes lösung hört sich für mich irgendwie interessanter an
und mit while schleifen hatte ich noch nicht so wirklich viel am hut


SmileySN - Mi 07.10.09 10:27

Ich rede doch von dem gleichen wie Lannes und dort wird auch von einer Schleife gesprochen.

Hier die einfache Lösung zum verstehen des Problemes:

Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
if pos('Information:', stringliste.strings[index]) >0  then   //nach string suchen
begin
  start := pos('[',stringliste.Strings[index+1]);
  ende  := Pos(']',Copy(stringliste.Strings[index+1],start,length(stringliste.Strings[index+1])));
  Memo2.Lines.Add(copy(stringliste.Strings[index+1],start,ende-1));

  start := pos('[',stringliste.Strings[index+2]);
  ende  := Pos(']',Copy(stringliste.Strings[index+2],start,length(stringliste.Strings[index+2])));
  Memo2.Lines.Add(copy(stringliste.Strings[index+2],start,ende-1));

  start := pos('[',stringliste.Strings[index+3]);
  ende  := Pos(']',Copy(stringliste.Strings[index+3],start,length(stringliste.Strings[index+3])));
  Memo2.Lines.Add(copy(stringliste.Strings[index+3],start,ende-1));
end;


Lannes - Mi 07.10.09 11:09

Hallo,
@user profile iconSmileySNnicht das Gleiche, aber ähnlich, mein Vorschlag ist nicht auf 3 Ergebnis-Zeilen fixiert. :wink:


user profile iconASMJmper hat folgendes geschrieben Zum zitierten Posting springen:
Lannes kannste deinen Pseudocode mal in einen code für delphi beginner schreiben


user profile iconLannes hat folgendes geschrieben Zum zitierten Posting springen:
Ich würde für die Interpretation der Daten While-Schleifen einsetzen,
Pseudocode:
- solange 'Information:' nicht enthalten ist, gehe weiter
- 'Information:' gefunden, erhöhe Index + 1
- solange Stop-Bedingung nicht erreicht, Einträge auswerten


gut, erkläre mal den Pseudocode:
solange ==> while <Bedingung> do
nicht => not
weiter => inc(Index)
{Index ist jetzt die Zeile in der die Bedingung erfüllt ist,
aber erst danach folgen die Werte, also}

erhöhe => inc(Index)
solange ==> while <Stop-Bedingung{z.B. Ende der Liste}> do
auswerten => Pos, copy, inc

Die fett-ausgezeichneten Begriffe in der Delphi-Hilfe nachlesen, dann sollte auch ein "Delphi-Beginner" den Pseudocode interpretieren und umsetzen können. :wink:


zuma - Mi 07.10.09 12:11

wenn ich mir die Aufgabenstellung anschauen, frage ich mich:
wäre das einfachste nicht das arbeiten mit indexof ? (wie bereits vorgeschlagen)

zuerst den Index der Start- und Endezeile ermitteln


Delphi-Quelltext
1:
2:
3:
4:
5:
start := stringliste.indexof('Information'); // liefert z.B. Zeile 5
// wenn Ende durch einen Text markiert wird
ende  := stringliste.indexof('irgendeinTextderdasEndemarkiert'); // z.b. [/Information] liefert z.B. Zeile 12
// wenn von start bis ende der Datei ausgelesen werden soll
ende  := Stringliste.count;  // liefert z.B. Zeile 20

dann die gewünschten Zeilen ins Memo übertragen

Delphi-Quelltext
1:
2:
3:
4:
5:
if start >= 0 then  // (Start-) Zeile überhaupt gefunden? ist -1, wenn nicht mit indexof ermittelt
begin
 for i := start to ende do
 memo.Lines.add(stringliste.strings[i]); 
end;


ASMJmper - Mi 07.10.09 14:50

lannes kommt das deinem Pseudocode nahe ? :)


Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
while not (pos('Information:', stringliste.strings[index]) >0do
    begin
    inc(index);
    end;
          while (pos('Information:', stringliste.strings[index]) >0do
          begin
              inc(index);
              while (index <= pred(stringliste.Count)) do
              begin
                start := pos('[',stringliste.Strings[index]);
                ende := Pos(']',Copy(stringliste.Strings[index],start,length(stringliste.Strings[b])));
                Memo1.Lines.Add(copy(stringliste.Strings[index],start,ende));
                inc(index);
end;end;





aber danke schon mal an alle für eure posts und hilfe


Lannes - Mi 07.10.09 17:17

Hallo,

user profile iconASMJmper hat folgendes geschrieben Zum zitierten Posting springen:
lannes kommt das deinem Pseudocode nahe ? :)
sagen wir mal näher :wink:

ich reduzier/formatiere/kommentiere mal Deinen Code ein wenig:

Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
15:
while not (pos('Information:', stringliste[index]) >0do                        // *[1]
  begin                                                                       // *[2] 
  inc(index);
  while (pos('Information:', stringliste[index]) >0do                         // *[3]
    begin
    inc(index);
    while (index <= stringliste.Count) do                                     // *[4]
      begin
      start := pos('[',stringliste[index]);
      ende := Pos(']',Copy(stringliste[index],start,length(stringliste[b])));
      Memo1.Lines.Add(copy(tabel[index],start,ende));                        //*[5]
      inc(index);
      end;
    end;
  end;



[1] Index ist noch nicht initialisiert, er soll doch bei Index 0 anfangen, und nicht bei einer zufälligen Index

[2] durch den begin-end-Block includierst Du schon Pos, Copy etc., es soll doch erstmal nur 'Information:' gesucht werden

[3] warum nochmal die Bedingung stellen? gibt es dafür einen Grund

[4] da knallt es "Maximum überschritten" weil:
Der Index bei einer Liste beginnt mit 0, Count beinhaltet die Anzahl der Strings[].
Index...Count
..0.......1
..1.......2
..2.......3
mit der Bedingung <= Count erlaubst Du einen Zugriff auf den Index 3, den es aber nicht gibt, die Folge ist eine Zugriffsverletzung, immer mit Count -1 oder Pred(Count) arbeiten.

[5] Du ermittelst die Positionen aus stringliste[index] greift dann auf irgendwas zu das "table" heißt :roll:

Hier mal das Grundgerüst das sich aus dem Psoudocode ergibt:

Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
Index := 0  // initialisieren
while Bedingung do  //weiter
  inc(Index);
// gefunden
inc(Index);  //erhöhen und dann die Auswertung beginnen
while Stop-Bedingung do
  begin
  //auswerten
  //hochzählen
  end;


Noch eine Anmerkung zu IndexOf:
Das ist nur dann anwendbar, wenn der Suchstring genau einem String in der StringList entspricht.


ASMJmper - Mi 07.10.09 18:56

ups
das mit dem

Delphi-Quelltext
1:
2:
3:
4:
5:
Index := 0  // initialisieren

und den

Memo1.Lines.Add(copy(tabel.Strings[index],start,ende));


war n copy & paste fehler :oops:


vielen dank :)

ps.
pred(stringliste.Count) ftw xD
hab heute keine zeit mehr werde morgen dann den fertigen code posten


thepaine91 - Do 08.10.09 09:17

lannes mir ging es in der Zeile mit Strings[] umd das b wollte lediglich wissen woher das kommt.