Entwickler-Ecke
Delphi Language (Object-Pascal) / CLX - copy, pos, string zerlegen, HILFE
napsterforever - Di 30.06.09 00:04
Titel: copy, pos, string zerlegen, HILFE
Hallo,
ich habe folgenden quelltext (x):
Quelltext
1: 2: 3: 4: 5: 6: 7: 8: 9:
| playerInfo.phtml?pid=4592112','c41c569a1b9c46c4cbc4bc58f37cb05f'))">Vorname Nachname</a> <img src="getImg.phtml?cid=1" alt="Meisterschale" title="Meisterschale"></td><td align="right">0</td><td align="right">47.660.000</td></tr> playerInfo.phtml?pid=4584708','c41c569a1b9c46c4cbc4bc58f37cb05f'))">Vorname2 Nachname2</a></td><td align="right">0</td><td align="right">36.530.000</td></tr> playerInfo.phtml?pid=4577749','c41c569a1b9c46c4cbc4bc58f37cb05f'))">Vorname3</a></td><td align="right">0</td><td align="right">36.010.000</td></tr> playerInfo.phtml?pid=4576634','c41c569a1b9c46c4cbc4bc58f37cb05f'))">Vorname5 Nachname</a></td><td align="right">0</td><td align="right">33.005.000</td></tr> playerInfo.phtml?pid=4587566','c41c569a1b9c46c4cbc4bc58f37cb05f'))">Vorname Nachname</a></td><td align="right">0</td><td align="right">30.590.000</td></tr> playerInfo.phtml?pid=5585080','c41c569a1b9c46c4cbc4bc58f37cb05f'))">Vorname</a></td><td align="right">0</td><td align="right">29.400.000</td></tr> playerInfo.phtml?pid=4643690','c41c569a1b9c46c4cbc4bc58f37cb05f'))">Nachname</a></td><td align="right">0</td><td align="right">25.600.000</td></tr> playerInfo.phtml?pid=4581018','c41c569a1b9c46c4cbc4bc58f37cb05f'))">Vorname Nachname</a></td><td align="right">0</td><td align="right">16.620.000</td></tr> playerInfo.phtml?pid=4576642','c41c569a1b9c46c4cbc4bc58f37cb05f'))">Vorname Nachname</a> <img src="getImg.phtml?cid=2" alt="Rote Laterne" title="Rote Laterne"></td><td align="right">0</td><td align="right">14.670.000</td></tr> |
und möchte nun die Namen und die dahinterstehenden Zahlen herausfiltern!
Also: Vorname Nachname 47.660.000
Vorname2 Nachname2 36.530.000
Vorname3 36.010.000
nun scheitere ich bereits an den namen, da ich nicht weis wie ich die position im string bestimmen soll!
mein erster versuch:
Quelltext
1:
| mem_Anzeige.Lines.Add(Copy(x,Pos('playerInfo.phtml?pid=4584708'+#39,x)+68,(Pos('</a></td><td align="right">',x)-(Pos('playerInfo.phtml?pid=4584708'+#39,x)+68)))); |
funktioniert auch für eine zeile ganz gut :D, aber eben nicht für alle da ja in jeder zeile z.b. </a></td><td align="right"> steht und ich somit keine eindeutige pos bestimmen kann!
hoffe es blickt da jmd durch und kann mir einen tipp geben!
//Edit: Habe überlegt jedesmal den string zu kürzen:
Quelltext
1: 2: 3: 4: 5:
| mem_Anzeige.Lines.Add(Copy(x,Pos('playerInfo.phtml?pid=4584708'+#39,x)+68,(Pos('</a></td><td align="right">',x)-(Pos('playerInfo.phtml?pid=4584708'+#39,x)+68)))); x:= Copy(x,Pos('playerInfo.phtml?pid=4584708'+#39,x)+100,3000); mem_Anzeige.Lines.Add(Copy(x,Pos('playerInfo.phtml?pid=4577749'+#39,x)+68,(Pos('</a></td><td align="right">',x)-(Pos('playerInfo.phtml?pid=4577749'+#39,x)+68)))); x:= Copy(x,Pos('playerInfo.phtml?pid=4577749'+#39,x)+100,3000); mem_Anzeige.Lines.Add(Copy(x,Pos('playerInfo.phtml?pid=4576634'+#39,x)+68,(Pos('</a></td><td align="right">',x)-(Pos('playerInfo.phtml?pid=4576634'+#39,x)+68)))); |
aber irgendwie scheint mir das alles zu umständlich und
ausserdem wechseln die zeilen ständig, sprich sortiert nach der zahl!
jaenicke - Di 30.06.09 00:39
Wie wäre es so? Dann wäre auch eine Fehlerbehandlung dabei...
Delphi-Quelltext
1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18: 19: 20: 21: 22: 23: 24: 25: 26: 27: 28: 29: 30: 31: 32: 33: 34: 35: 36: 37: 38: 39: 40: 41: 42: 43: 44: 45: 46: 47: 48:
| function ExtractValues(const AText: string; var AName, ANumber: string): Boolean; const NameStart = '''))">'; NameEnd = '</a>'; NumberEnd = '</td></tr>'; var CurrentText: PChar; FoundPos: Integer; begin Result := False; FoundPos := Pos(NameStart, AText); if FoundPos = 0 then Exit; CurrentText := @AText[FoundPos + Length(NameStart)]; FoundPos := Pos(NameEnd, CurrentText); if FoundPos = 0 then Exit; AName := Copy(CurrentText, 1, FoundPos - 1); FoundPos := Pos(NumberEnd, CurrentText); if FoundPos = 0 then Exit; Inc(CurrentText, FoundPos); FoundPos := 0; while CurrentText^ <> '>' do begin Dec(CurrentText); Inc(FoundPos); end; ANumber := Copy(CurrentText, 2, FoundPos - 2); Result := True; end;
procedure TForm214.Button1Click(Sender: TObject); var ExtractedName, ExtractedNumber: String; i: Integer; begin for i := 0 to Memo1.Lines.Count - 1 do if ExtractValues(Memo1.Lines[i], ExtractedName, ExtractedNumber) then ShowMessage(ExtractedName + #13#10 + ExtractedNumber) else ShowMessage(Memo1.Lines[i]); end; |
napsterforever - Di 30.06.09 13:27
das ist ja genial :D
ich will jetzt die namen und zahlen in einem memo oder grid ausgeben lassen, also
Name Zahl
Name2 Zahl2 usw
die berechnung soll aber im hintergrund laufen, kann ich den quelltext nur in ein memo schreiben und dann die namen raussorterien?
Quelltext
1: 2: 3: 4:
| for i := 0 to mem_berechnung.Lines.Count - 1 do if ExtractValues(Mem_berechnung.Lines[i], ExtractedName, ExtractedNumber) then //ShowMessage(ExtractedName + #13#10 + ExtractedNumber) Mem_anzeige.Lines.add(ExtractedName + #13#10 + ExtractedNumber) |
wenn ich das mem_berechnung klein und visible:=false setze funktioniert es nicht mehr!
ich bin leider in delphi (noch) nicht sehr bewandert ;-(
jaenicke - Di 30.06.09 14:23
Willst du die Ergebnisse jetzt in einem Memo dem Benutzer anzeigen oder willst du die nur im Programm speichern und benutzen? :gruebel:
Und was "funktioniert nicht mehr"?
napsterforever - Di 30.06.09 16:22
ich will die ergebnisse dem benutzer in einem memo oder besser noch in einer tabelle anzeigen, ich weiss nur nicht recht wie ich deine function verwenden muss!
Hatte irgendwie den quelltext in ein mem_berechnung geschrieben und dann mit deiner function die einzelnen zeilen eben untersuchen lassen und die namen ausgegeben in einem anderen mem_anzeigen!
Die berechnung im mem_berechnen soll aber im hintergrund laufen, aber wenn ich das memofeld irgendwie kleiner mache und visible:=false setze geht das nicht mehr s.o.! ich weiss leider nicht recht wie ich es anders machen soll :D
jaenicke - Di 30.06.09 16:25
Wie du es immer schaffst dich mit so wenigen Worten so klar auszudrücken... jetzt weiß ich natürlich ganz genau was du meinst was da falsch läuft... :roll:
Wieviele Zeilen sind das denn, dass das im Hintergrund laufen muss? Lines.BeginUpdate / Lines.EndUpdate könnten helfen.
Ich rate einmal ins Blaue...
Wenn du die Zeilenumbrücke weg haben willst, setze WordWrap auf False.
Wenn du ScrollBars haben willst, setze die entsprechende Eigenschaft.
Wenn das Programm abstürzt, nimm den Debugger und schau was passiert...
Wenn das Memo gar nicht mehr zu sehen ist, setze Visible danach wieder auf True.
napsterforever - Di 30.06.09 16:39
jaenicke hat folgendes geschrieben : |
| Wie du es immer schaffst dich mit so wenigen Worten so klar auszudrücken... jetzt weiß ich natürlich ganz genau was du meinst was da falsch läuft... :roll: |
ja wie oben bereits geschrieben eben xD
sieht also so aus:
Delphi-Quelltext
1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11:
| procedure TForm1.but_spielstandClick(Sender: TObject); var x,str,ExtractedName, ExtractedNumber: String; i: Integer; begin x := idhttp1.GET('http://www.comunio.de/standings.phtml'); mem_berechnung.text := Copy(x,Pos('playerInfo.phtml?pid=4592112',x)+2,2000); for i := 0 to mem_berechnung.Lines.Count - 1 do if ExtractValues(Mem_berechnung.Lines[i], ExtractedName, ExtractedNumber) then Mem_anzeige.Lines.add(ExtractedName + #13#10 + ExtractedNumber) end; |
//Wenn ich auf den Button klicke soll dem benutzer in einem memo oder einer tabelle
Name Zahl
Name2 Zahl2 etc ausgegeben werden
| Zitat: |
Wieviele Zeilen sind das denn, dass das im Hintergrund laufen muss? Lines.BeginUpdate / Lines.EndUpdate könnten helfen. |
ja wie siehe oben :D, ich weiss ja nicht mal ob das im hintergrund laufen muss, das ist ja meine frage wie ich deine function für mein vorhaben am besten anwenden kann.
ich will diesen "ausschnitt" des quelltextes von /standings.phtml:
Quelltext
1: 2: 3: 4: 5: 6: 7: 8: 9:
| playerInfo.phtml?pid=4592112','c41c569a1b9c46c4cbc4bc58f37cb05f'))">Vorname Nachname</a> <img src="getImg.phtml?cid=1" alt="Meisterschale" title="Meisterschale"></td><td align="right">0</td><td align="right">47.660.000</td></tr> playerInfo.phtml?pid=4584708','c41c569a1b9c46c4cbc4bc58f37cb05f'))">Vorname2 Nachname2</a></td><td align="right">0</td><td align="right">36.530.000</td></tr> playerInfo.phtml?pid=4577749','c41c569a1b9c46c4cbc4bc58f37cb05f'))">Vorname3</a></td><td align="right">0</td><td align="right">36.010.000</td></tr> playerInfo.phtml?pid=4576634','c41c569a1b9c46c4cbc4bc58f37cb05f'))">Vorname5 Nachname</a></td><td align="right">0</td><td align="right">33.005.000</td></tr> playerInfo.phtml?pid=4587566','c41c569a1b9c46c4cbc4bc58f37cb05f'))">Vorname Nachname</a></td><td align="right">0</td><td align="right">30.590.000</td></tr> playerInfo.phtml?pid=5585080','c41c569a1b9c46c4cbc4bc58f37cb05f'))">Vorname</a></td><td align="right">0</td><td align="right">29.400.000</td></tr> playerInfo.phtml?pid=4643690','c41c569a1b9c46c4cbc4bc58f37cb05f'))">Nachname</a></td><td align="right">0</td><td align="right">25.600.000</td></tr> playerInfo.phtml?pid=4581018','c41c569a1b9c46c4cbc4bc58f37cb05f'))">Vorname Nachname</a></td><td align="right">0</td><td align="right">16.620.000</td></tr> playerInfo.phtml?pid=4576642','c41c569a1b9c46c4cbc4bc58f37cb05f'))">Vorname Nachname</a> <img src="getImg.phtml?cid=2" alt="Rote Laterne" title="Rote Laterne"></td><td align="right">0</td><td align="right">14.670.000</td></tr> |
eben so bearbeiten, dass ich nachher nur noch name und zahl habe!
Moderiert von
Narses: Code- durch Delphi-Tags ersetzt
jaenicke - Di 30.06.09 16:41
Das macht der Quelltext bei mir auch problemlos aus den Zeilen. :nixweiss:
Was läuft denn nun falsch?
Loggst du dich denn überhaupt vorher mit der Indy-Komponente ein?
(Und wenn es das wirklich ist, dann hättest du das im Debugger längst sehen können, dass da was falsches ankommt...)
// EDIT:
Nebenbei: Wozu das Memo mem_berechnung, wenn du offenbar gar nicht nachschaust was darin ankommt? Und wenn das im Programm dann gar nicht zu sehen sein soll, reicht auch eine TStringList.
napsterforever - Di 30.06.09 16:53
jaenicke hat folgendes geschrieben : |
Loggst du dich denn überhaupt vorher mit der Indy-Komponente ein?
(Und wenn es das wirklich ist, dann hättest du das im Debugger längst sehen können, dass da was falsches ankommt...) |
eingeloggt bin ich definitiv sonst würde ich nicht auf die /standings.phtml zugriffen können bzw mir würde ja nichts angezeigt. ich bekomme aber je nachdem wie ich eben das mem_berechnung in seiner größe verändere die namen und zahlen nachher im mem_anzeige angezeigt, um so größer das memo umso mehr namen und zahlen?!^^
jaenicke hat folgendes geschrieben : |
| Nebenbei: Wozu das Memo mem_berechnung, wenn du offenbar gar nicht nachschaust was darin ankommt? Und wenn das im Programm dann gar nicht zu sehen sein soll, reicht auch eine TStringList. |
ich lasse mir das mem_berechnung ja auch anzeigen und wenn ich
Delphi-Quelltext
1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11:
| procedure TForm1.but_spielstandClick(Sender: TObject); var x,str,ExtractedName, ExtractedNumber: String; i: Integer; begin x := idhttp1.GET('http://www.comunio.de/standings.phtml'); mem_berechnung.text := Copy(x,Pos('playerInfo.phtml?pid=4592112',x)+2,2000); for i := 0 to mem_berechnung.Lines.Count - 1 do if ExtractValues(Mem_berechnung.Lines[i], ExtractedName, ExtractedNumber) then Mem_anzeige.Lines.add(ExtractedName + #13#10 + ExtractedNumber) end; |
ausführe, dann steht nachher der relevante teil der standings.phtml, also Copy(x,Pos('playerInfo.phtml?pid=4592112',x)+2,2000);, im mem_berechnen, ist ja auch logisch^^
Dass ich das mem_berechnen wahrscheinlich gar nicht brauche vermute ich ja, mein vorhaben ist wie gesagt bloß die namen und zahlen aus dieser standings.phtml in einem memo oder tabelle anzeigen zu lassen, mehr will ich ja gar nicht :D
mit tstringlist weiss ich nicht wie ich das machen muss
Moderiert von
Narses: Code- durch Delphi-Tags ersetzt
napsterforever - Di 30.06.09 17:22
ich glaube du weisst nicht recht was ich meine :cry:
ich will keine scrollbalken und das verdammte mem_berechnen ja gar nicht haben,
ich will bloß namen und zahlen in mem_anzeige anzeigen lassen!
sag mir einfach wie ich das am besten machen :-)
ich habe
a) einen html quelltext von /standings.phtml
b) ein memo feld (mem_anzeigen)
c) deine function
und d) einen button (but_spielstand)!
man stelle sich also vor, auf dem formular (der anwendungsoberfläche, die der benutzer sieht) befinden sich zwei edit felder und ein loginbutton zur anmeldung, ein spielstand-anzeigenbutton und ein memo feld darüber!
Man loggt sich ein, klickt auf den spielstand-anzeigenbutton und SOLL dann einfach nur den spielstand im memo feld (im letzteren mem_anzeige genannt) angezeigt bekommen, also vorerst:
Name Zahl
Name2 Zahl2
asdlkasjd 23213
asldkjawd 2323
ljasdla 2323
p.s. sry aber ich bin mit delphi absolut nicht lange vertraut und danke für deine viele mühe, hoffe du verstehst überhaupt was ich vor habe jetzt xD
jaenicke - Di 30.06.09 17:28
Ach so, jetzt verstehe ich, dass dein Memo als Zwischenspeicher zu klein ist, ist das Problem...
Die Zeilen werden umgebrochen, weil WordWrap auf True ist bei dir.
Auch das hatte ich oben schon geschrieben...
Das ist genau eines der vielen Probleme, wenn man visuelle Komponenten als Zwischenspeicher missbraucht... :roll:
Delphi-Quelltext
1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17:
| procedure TForm1.but_spielstandClick(Sender: TObject); var i: Integer; PageContents: TStringList; ExtractedName, ExtractedNumber: String; begin PageContents := TStringList.Create; try PageContents.Text := IdHttp1.Get('http://www.comunio.de/standings.phtml'); PageContents.Text := Copy(PageContents.Text, Pos('playerInfo.phtml?pid=4592112', PageContents.Text) + 2, 2000); for i := 0 to PageContents.Count - 1 do if ExtractValues(PageContents[i], ExtractedName, ExtractedNumber) then Mem_anzeige.Lines.add(ExtractedName + #13#10 + ExtractedNumber) finally PageContents.Free; end; end; |
napsterforever - Di 30.06.09 17:38
jawoll jetzt nimmt das ganze doch schon formen an, vielen vielen dank für die mühe :D
jetzt muss ich das nur noch irgendwie tabellarisch hinkriegen und die punkte noch rausfiltern, aber danke erstmal soweit ;-)
jaenicke - Di 30.06.09 17:48
Tabellarisch: Nimm TListView statt nem Memo. ;-)
napsterforever - Di 30.06.09 19:12
jaenicke hat folgendes geschrieben : |
| Tabellarisch: Nimm TListView statt nem Memo. ;-) |
hmm war mal wieder eine schwierige geburt bis ich Tlistview verstanden habe, AAAABER immerhin hab ichs hinbekommen ;-)
Delphi-Quelltext
1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18: 19: 20: 21: 22: 23: 24: 25:
| procedure TForm1.but_spielstandClick(Sender: TObject); var i: Integer; PageContents: TStringList; ExtractedName, ExtractedNumber: String; L: TListItem; begin if lab_status.Caption = 'Du bist Eingeloggt' = true then begin PageContents := TStringList.Create; try PageContents.Text := IdHttp1.Get('http://www.comunio.de/standings.phtml'); PageContents.Text := Copy(PageContents.Text, Pos('<tr class="tablecontent01">', PageContents.Text) + 2, 5000); for i := 0 to PageContents.Count - 1 do if ExtractValues(PageContents[i], ExtractedName, ExtractedNumber) then begin L := liv_anzeige.items.add; L.Caption := (ExtractedName); L.SubItems.Add(ExtractedNumber); end; finally PageContents.Free; end; end; end; |
YES, ich mache fortschritte, und nochmals danke für die mühe :-)
Moderiert von
Narses: Code- durch Delphi-Tags ersetzt
napsterforever - Di 30.06.09 20:14
ok, wieder was gelernt :-)
---
Moderiert von
Narses: Beiträge zusammengefasst---
noch eine Frage:
Delphi-Quelltext
1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18: 19: 20: 21: 22: 23: 24: 25: 26: 27: 28: 29: 30: 31: 32: 33: 34: 35: 36:
| procedure TForm1.but_loginClick(Sender: TObject); var s:string; stream: TStringList; begin try try IdHttp1.HandleRedirects := true; IdHTTP1.AllowCookies:=true; IdHTTP1.CookieManager:=IdCookieManager1; stream := TStringList.Create; Stream.Add('login='+edt_Benutzername.Text); Stream.Add('pass='+edt_Passwort.Text); Stream.Add('action=login'); Stream.Add('%3E%3E+Login_x=33');
s := idhttp1.Post('http://www.comunio.de/login.phtml',stream);
if (Pos('Logout',s) > 0) then begin ShowMessage('Du bist Eingeloggt.'); lab_status.Caption := 'Du bist Eingeloggt'; end; if (Pos('Logout',s) = 0) then begin ShowMessage('E-Mail-Adresse oder Passwort falsch ODER Server-Überlastung'); lab_status.Caption := 'Du bist Ausgeloggt'; but_loginhack.Enabled := true; end; finally Stream.Free; end; except on E: Exception do ShowMessage(E.Message); end; end; |
Wenn ich auf den Button klicke kommt zunächst immer die Fehlermeldung 'E-Mail-Adresse oder Passwort falsch ODER Server-Überlastung'. Erst beim zweiten klick auf den Button loggt er sich ein, warum?
Moderiert von
Narses: Code- durch Delphi-Tags ersetzt
jaenicke - Di 30.06.09 20:16
Schau dir eben den Inhalt von s an, da sollte ja eine Meldung oder so drin stehen...
napsterforever - Di 30.06.09 20:25
hmm wenn ichs so mache
Delphi-Quelltext
1: 2: 3: 4:
| idhttp1.Post('http://www.comunio.de/login.phtml',stream); s := idhttp1.Post('http://www.comunio.de/login.phtml',stream);
if (Pos('Logout',s) > 0) then |
gehts :-)
Moderiert von
Narses: Code- durch Delphi-Tags ersetzt
jaenicke - Di 30.06.09 20:27
Naja, sicher, aber du hättest ja auch einfach einmal schauen können was da für eine Meldung kommt. Vielleicht lässt sich das ja beheben.
Du brauchst das ja nur in ein Memo oder so schnell mal schreiben um dir anzuschauen was da zurückkommt.
napsterforever - Di 30.06.09 22:40
mal davon abgesehen, wie realisiere ich am besten eine Speicherung der login-Daten?
Hab mir das so vorgestellt:
Wenn ich im Programm Benutzername und Passwort eingebe und auf Login klicke, und dabei ein RadioButton oder eine Checkbox aktiviert ist, werden die Benutzerdaten in einer Profil.dat gespeichert und beim nächsten Programmstart wieder in die Editfelder (Benutzername und Passwort) geladen!
Dazu habe ich folgendes gefunden:
Delphi-Quelltext
1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18: 19: 20: 21:
| procedure TForm1.LoadFromFile(Datei:string); var Liste : TStringlist; begin Liste:=TStringList.Create; Liste.LoadFromFile(Datei); edt_benutzername.text:=Liste.IndexOf('Name'); edt_passwort.text:=Liste.IndexOf('Passwort'); Liste.Free; end;
procedure TForm1.SaveToFile(Datei:string); var Liste : TStringlist; begin Liste:=TStringList.Create; Liste.Add('Name='+edt_benutzername.text); Liste.Add('Passwort='+edt_passwort.text); Liste.SaveToFile(Datei); Liste.Free; end; |
Bei edt_benutzername.text:=Liste.IndexOf('Name'); kommt aber [Fehler] comunio_tool.pas(131): Inkompatible Typen: 'String' und 'Integer', wenn ich inttostr davor mache kommt bullshit raus
Moderiert von
Narses: Code- durch Delphi-Tags ersetzt
jaenicke - Di 30.06.09 22:42
Wie wäre es mit Liste.Values['Name']? ;-)
Aber: neue Frage --> Neuer Thread!
napsterforever - Di 30.06.09 22:54
jaenicke hat folgendes geschrieben : |
Wie wäre es mit Liste.Values['Name']? ;-)
Aber: neue Frage --> Neuer Thread! |
omg das funktioniert :D
wie kannst du das nur alles wissen, hast du delphi selbst geschrieben oder kommst du aus borland?^^
Entwickler-Ecke.de based on phpBB
Copyright 2002 - 2011 by Tino Teuber, Copyright 2011 - 2026 by Christian Stelzmann Alle Rechte vorbehalten.
Alle Beiträge stammen von dritten Personen und dürfen geltendes Recht nicht verletzen.
Entwickler-Ecke und die zugehörigen Webseiten distanzieren sich ausdrücklich von Fremdinhalten jeglicher Art!