Autor Beitrag
SchelmVomElm
ontopic starontopic starontopic starontopic starontopic starofftopic starofftopic starofftopic star
Beiträge: 154

W2K Pro
D5 Pro
BeitragVerfasst: Mo 21.03.05 13:07 
Also wie das gehen soll ist mir auch nicht klar! Wenn WordPos in der Schleife nicht 0 erreicht hat die Funktion nicht mal einen definierten Rückgabewert! Also, was soll das?

_________________
for(;P("\n"),R--;P("|"))for(e=C;e--;P("_"+(*u++/8)%2))P("|"+(*u/4)%2);
F34r0fTh3D4rk
ontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic starofftopic star
Beiträge: 5284
Erhaltene Danke: 27

Win Vista (32), Win 7 (64)
Eclipse, SciTE, Lazarus
BeitragVerfasst: Mo 21.03.05 14:38 
ausblenden Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
15:
16:
17:
18:
19:
20:
21:
22:
Function WortExtrahieren(Text: string; Wort: Word; Trennzeichen: Char): string;  
var  
 p  : PChar;  
begin  
  p  := PChar(Text);  
  repeat  
    Dec(Wort);  
    while p^ <> Trennzeichen do  
    begin  
      if Wort = 0 then  
       Result := Result + p^;  
      Inc(p);  
    end;  
    if Wort = 0 then Exit;  
    Inc(p);  
  until p^ = Trennzeichen;  
end

//Beispiel
str:= 'Hallo;Du;Da';
str2:= WortExtrahieren(str, 1';');
//Dann ist str2 = Hallo
delfiphan
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic star
Beiträge: 2684
Erhaltene Danke: 32



BeitragVerfasst: Mo 21.03.05 14:44 
Mit dem Beispiel wird's schon viel klarer. :)
Scheint zu funktionieren, nur: Das letzte Wort lässt sich nicht korrekt extrahieren:
ausblenden Delphi-Quelltext
1:
WortExtrahieren('a;b;c',3,';'); // Der zurückgegebene String ist 100 Zeichen gross!					

Und: Wie weiss ich eigentlich, dass ich am Ende des Strings bin?
WortExtrahieren('a;b;c',4,';');gibt eine Endlosschleife. Ausserdem kann das String auch mal leer sein...
F34r0fTh3D4rk
ontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic starofftopic star
Beiträge: 5284
Erhaltene Danke: 27

Win Vista (32), Win 7 (64)
Eclipse, SciTE, Lazarus
BeitragVerfasst: Mo 21.03.05 14:47 
ich habe gerade einen fehler in delphi enddeckt, ich habe ein wort per random auswählen und als showmessage anzeigen lassen, wenn das letzte wort ausgewählt wurde kommt kein msg fenster sondern ein formular mit unendlicher breite und links oben ein label auf dem das wort steht, ok button fehlt und X lässt sich auch net erreichen, weils nach rechts hin unendlich lang ist. :shock:
retnyg
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starofftopic star
Beiträge: 2754

SNES, GB, GBA, CPC, A500, 486/66, P4/3.0HT: NintendOS, AmigaOS, DoS
Delphi 5, Delphi 7
BeitragVerfasst: Mo 21.03.05 14:48 
wenn ich das richtig sehe wird bei dunkelfürchters code einfach der pointer erhöht, was ein speicherleck erzeugt, der PChar kann nicht mehr freigegeben werden weil der pointer nicht mehr passt

_________________
es gibt leute, die sind genetisch nicht zum programmieren geschaffen.
in der regel haben diese leute die regel...
F34r0fTh3D4rk
ontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic starofftopic star
Beiträge: 5284
Erhaltene Danke: 27

Win Vista (32), Win 7 (64)
Eclipse, SciTE, Lazarus
BeitragVerfasst: Mo 21.03.05 14:50 
ich glaube der fehler, dass das letzte wort net ausgelesen wird lässt sich so beheben:
ausblenden Delphi-Quelltext
1:
str:= 'Hallo;Du;Da;';					
delfiphan
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic star
Beiträge: 2684
Erhaltene Danke: 32



BeitragVerfasst: Mo 21.03.05 14:52 
Wollt ich soeben auch schreiben. @F34r0fTh3D4rk: Das ist kein Delphi-Fehler, sondern ein Folgefehler wegen deiner Prozedur. Auch wenn der Pointer korrekt vernichtet würde spuckt deine Prozedur Unsinn beim letzten Wort aus: Du testest nirgends auf das Ende des Strings!!

//Edit: Hab deinen Post erst jetzt gelesen. Lässt sich so nur bedingt beheben... Das ist doch keine Lösung ;) Woher soll man überhaupt wissen, wieviele Einträge der String hat? Die Strings kommen aus einer Datei, da kann eine Zeile auch mal leer sein!!

Wie dem auch sei: Die ursprüngliche Frage ist schon längst beantwortet. Lassen wir's sein!
F34r0fTh3D4rk
ontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic starofftopic star
Beiträge: 5284
Erhaltene Danke: 27

Win Vista (32), Win 7 (64)
Eclipse, SciTE, Lazarus
BeitragVerfasst: Mo 21.03.05 15:04 
ich habs gerade so versucht, das ist aber schwachsinn, wie kann ich denn in meinem code das ende des strings abfragen ohne extra noch einen zähler einzubauen ?
ausblenden Delphi-Quelltext
1:
until (p^ = Trennzeichen) or (not (ord(p^) in [1..255])); //<- das gleiche wie (p^ = #0)					
delfiphan
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic star
Beiträge: 2684
Erhaltene Danke: 32



BeitragVerfasst: Mo 21.03.05 15:08 
p ist nullterminiert. Da brauchst du keinen Zähler. Du solltest aber eine while-Schleife benützen, da das erste Zeichen schon eine #0 sein kann.
Übrigens @retnyg: Gibt's wirklich ein Speicherleck? PChar liefert hier doch nur nen Zeiger auf Text zurück und alloziert keinen neuen Speicher.

//Edits 1,2: Sorry, komische Satzkonstruktionen geflickt ;)


Zuletzt bearbeitet von delfiphan am Mo 21.03.05 15:13, insgesamt 2-mal bearbeitet
F34r0fTh3D4rk
ontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic starofftopic star
Beiträge: 5284
Erhaltene Danke: 27

Win Vista (32), Win 7 (64)
Eclipse, SciTE, Lazarus
BeitragVerfasst: Mo 21.03.05 15:11 
genau :D
retnyg
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starofftopic star
Beiträge: 2754

SNES, GB, GBA, CPC, A500, 486/66, P4/3.0HT: NintendOS, AmigaOS, DoS
Delphi 5, Delphi 7
BeitragVerfasst: Mo 21.03.05 15:16 
Zitat:
ausblenden Delphi-Quelltext
1:
2:
3:
 p  : PChar;  
begin  
  p  := PChar(Text);

hier wird doch ein neuer PCHar erstellt, und der wert von text reinkopiert. danach wird der pointer "verbogen", wie soll der kompiler wissen was er nun wieder freigeben kann ?

_________________
es gibt leute, die sind genetisch nicht zum programmieren geschaffen.
in der regel haben diese leute die regel...
opfer.der.genauigkeit
ontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic starofftopic star
Beiträge: 754
Erhaltene Danke: 1



BeitragVerfasst: Mo 21.03.05 15:23 
Wieso sollte das n Speicherleck erzeugen?

p ist der Zeiger auf den String.
Der String wird von Delphi eh seperat behandelt.

p = pchar(s) und d.h. p ist der zeiger von s .. wird also s, von Delphi, freigegeben ist der pointer eh müll..
Sinnvoll wäre da noch p = nil. Schöner wär's allerdings.

Versucht mal den pointer so freizugegeben Dispose(p) .. viel Spaß mit der Exception.

_________________
Stellen Sie sich bitte Zirkusmusik vor.
F34r0fTh3D4rk
ontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic starofftopic star
Beiträge: 5284
Erhaltene Danke: 27

Win Vista (32), Win 7 (64)
Eclipse, SciTE, Lazarus
BeitragVerfasst: Mo 21.03.05 15:25 
Zitat:

Sinnvoll wäre da noch p = nil. Schöner wär's allerdings.

wo ?
retnyg
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starofftopic star
Beiträge: 2754

SNES, GB, GBA, CPC, A500, 486/66, P4/3.0HT: NintendOS, AmigaOS, DoS
Delphi 5, Delphi 7
BeitragVerfasst: Mo 21.03.05 15:26 
user profile iconopfer.der.genauigkeit hat folgendes geschrieben:
Wieso sollte das n Speicherleck erzeugen?

p ist der Zeiger auf den String.
Der String wird von Delphi eh seperat behandelt.

wäre p der zeiger auf einen string, würde das so aussehen:
ausblenden Delphi-Quelltext
1:
2:
3:
 p  : ^string;  
begin  
  p  := @Text;

_________________
es gibt leute, die sind genetisch nicht zum programmieren geschaffen.
in der regel haben diese leute die regel...
F34r0fTh3D4rk
ontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic starofftopic star
Beiträge: 5284
Erhaltene Danke: 27

Win Vista (32), Win 7 (64)
Eclipse, SciTE, Lazarus
BeitragVerfasst: Mo 21.03.05 15:26 
so funktionier das aber leider net
opfer.der.genauigkeit
ontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic starofftopic star
Beiträge: 754
Erhaltene Danke: 1



BeitragVerfasst: Mo 21.03.05 15:45 
Ok,

ich seh's ein.. blöd formuliert. :oops:

Du hast recht retnyg.. ist kein zeiger auf string.

*sfz*

Ok, besser ausgedrückt.

p := pchar(s);
Ein PChar ist ein Zeiger auf einen nullterminierten String mit Zeichen des Typs Char.

p muß und kann nicht freigegeben werden in diesem fall, da s von delphi eh freigegeben wird.
p zeigt aber weiterhin auf den Text, da Delphi den Speicher nicht mit Nullen vollschreibt, sondern nur die Referenz von s tötet.

Naja.. deshalb p := nil am Ende setzen, sofern man das möchte.

Würde man z.B. das hier machen:

ausblenden Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
15:
16:
17:
..
  private
    globalP: pchar;
..
var
  s: string;
  p: pchar;
begin
  s := 'test';
  p := pchar(s);
  globalP := p;
end;

procedure irgendwas;
begin
  showmessage(globalp); // hier wird noch test als resultat erscheinen.. wenn man glück hat. :) 
end;


Naja, ich hoffe meine Aussagen stimmen, sonst muß ich mich wohl heute einbuddeln und nochmal das Thema mit den Zeigern durchkämpfen. :roll:

_________________
Stellen Sie sich bitte Zirkusmusik vor.
F34r0fTh3D4rk
ontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic starofftopic star
Beiträge: 5284
Erhaltene Danke: 27

Win Vista (32), Win 7 (64)
Eclipse, SciTE, Lazarus
BeitragVerfasst: Mo 21.03.05 15:49 
oha, bin ich dumm, so muss es lauten:
ausblenden Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
15:
16:
17:
18:
19:
20:
21:
Function WortExtrahieren(Text: string; Wort: Word; Trennzeichen: Char): string;
var
 p  : PChar;
begin
  p:= PChar(Text);
  repeat
    Dec(Wort);
    while p^ <> Trennzeichen do
    begin
      if Wort = 0 then
        Result := Result + p^;
      if p^ = #0 then
        Exit;
      Inc(p);
    end;
    if Wort = 0 then
      Exit;
    Inc(p);
  until (p^ = Trennzeichen);
  P:= nil;
end;
SchelmVomElm
ontopic starontopic starontopic starontopic starontopic starofftopic starofftopic starofftopic star
Beiträge: 154

W2K Pro
D5 Pro
BeitragVerfasst: Mo 21.03.05 15:53 
p ist ein Zeiger auf das erste Zeichen des Strings.
Der Speicher für den gesammten nullterm. string ist reserviert.
Nach der Benutzung gibt Delphi den Speicher wieder frei.
Und zwar von p bis #0. p hat sich aber verändert und ob der Compiler das merkt und entsprechend handelt ist hier die Frage!
Durchaus diskussionswürdig wie ich finde - ich glaub das gibt 'nen Leck!

_________________
for(;P("\n"),R--;P("|"))for(e=C;e--;P("_"+(*u++/8)%2))P("|"+(*u/4)%2);
F34r0fTh3D4rk
ontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic starofftopic star
Beiträge: 5284
Erhaltene Danke: 27

Win Vista (32), Win 7 (64)
Eclipse, SciTE, Lazarus
BeitragVerfasst: Mo 21.03.05 15:55 
hier gehn die meinungen auseinander, wo ist der beweis ?
retnyg
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starofftopic star
Beiträge: 2754

SNES, GB, GBA, CPC, A500, 486/66, P4/3.0HT: NintendOS, AmigaOS, DoS
Delphi 5, Delphi 7
BeitragVerfasst: Mo 21.03.05 16:03 
ausblenden Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
procedure TForm1.Button1Click(Sender: TObject);
var  s: string;
     p:pchar;
     pp, ps: pointer;
begin
  s:='bla';
  p:=pchar(s);
  ps:=@s;
  pp:=@p;
  if ps <> pp then showmessage('uneven');
end;

hier dran sieht man, dass die funktion PChar(String) zuerst einen neuen, null-terminierten string erzeugt und anschliessend darauf zeigt, es wird also nicht einfach ein pointer auf den bereits existierenden string erstellt.

_________________
es gibt leute, die sind genetisch nicht zum programmieren geschaffen.
in der regel haben diese leute die regel...