Jump to content

Attila Kovacs

Members
  • Content Count

    1936
  • Joined

  • Last visited

  • Days Won

    25

Everything posted by Attila Kovacs

  1. Attila Kovacs

    Help with string extraction function

    Slightly modified Stefan's beautiful routine. If I did not screw it up, it's faster because of comparing against the stack (parameters aChar1, aChar2), (I can't explain that), and omitting "sr" leaves more register for the compiler, which was a speed boost again. Also, the initial "while" became a "repeat until", and instead of "P^ = #0" there is a " P = ep". function ExtractContent4(const S: string; const aChar1, aChar2: Char): string; var P, ep, r: PChar; len: integer; begin len := S.Length; if len = 0 then exit(S); SetLength(Result, len); r := Pointer(Result); P := Pointer(S); ep := P + len; repeat r^ := P^; if P^ = aChar1 then begin repeat inc(P); until (P^ = aChar2) or (P = ep); end else inc(r); inc(P); until P > ep; SetLength(Result, r - Pointer(Result)); end;
  2. Attila Kovacs

    Help with string extraction function

    no-no, the compiler runs out of registers if do so, always testing separately Nice routine. I don't know why but if you use parameters instead if consts it performs even better. (Despite comparing against the stack) ExtractContent(const S: string; const aChar1, aChar2: Char); this boost it even further: var zero: Char; zero := #0; until (P^ = aChar2) or (P^ = zero); or even better: until (P^ = aChar2) or (P = ep);
  3. Attila Kovacs

    Help with string extraction function

    Looking into the Move() implementation, wth is happened to rep movs*? Is it too slow nowadays?
  4. Attila Kovacs

    Help with string extraction function

    You are right, even around the Move() was some string magic. With passing PChar is even faster. As for the result type, I'll let it for Mike to tune it.
  5. Attila Kovacs

    Help with string extraction function

    @Mike Torrettinni Slightly modified, wasn't round everything.
  6. Attila Kovacs

    Help with string extraction function

    Player 3 entered the game (edited) function RemoveTextBetweenChars(const aString: string; const aChar1, aChar2: Char): string; label exit; var c: integer; P, start, res: PChar; begin if aString <> '' then begin SetLength(Result, aString.Length); res := Pointer(Result); P := Pointer(aString); c := 0; while True do begin start := P; while P^ <> aChar1 do begin inc(P); if P^ = #0 then begin Move(start^, res[c], (P - start) * SizeOf(Char)); inc(c, P - start); goto exit; end; end; Move(start^, res[c], (P - start) * SizeOf(Char)); inc(c, P - start); while P^ <> aChar2 do begin inc(P); if P^ = #0 then goto exit; end; inc(P); if P^ = #0 then goto exit; end; exit: SetLength(Result, c); end; end;
  7. Attila Kovacs

    Are we just "Cash Cows"?

    they are busy with bumping Delphi 7 licences
  8. Attila Kovacs

    how to send byte array with TWSocketClient

    Move( PFirmWare(FXmodemFile.Items[Line])^.buffer, buffer[0], Length(PFirmWare(FXmodemFile.Items[Line])^.buffer) );
  9. Attila Kovacs

    Centered message?

    No, this is the good thing ๐Ÿ˜‰ I've a batch file for building the release versions.
  10. Attila Kovacs

    ctrl+b on the welcome page

    @limelect thx for confirming. It was acquired by emba, It's in getit, so there will be no new releases for older IDE's.
  11. Attila Kovacs

    How to increase the distance between TCheckBox glyph and caption text?

    All good. It was in my comment that this is only for static text, and if you would argue then you should have asked what if somebody want 2.5 x space distance ๐Ÿ˜‰
  12. Attila Kovacs

    How to increase the distance between TCheckBox glyph and caption text?

    btw. how did you separate the words back in the high school?
  13. Attila Kovacs

    How to increase the distance between TCheckBox glyph and caption text?

    of course does it work, just set the font size to 2. what is your problem?
  14. Attila Kovacs

    How to increase the distance between TCheckBox glyph and caption text?

    Only if the text is dynamic or multilang. So in 99.99% the cases could work. Caption = ' Unga'#13#10' Bunga' WordWrap = True
  15. Attila Kovacs

    Ctrl Tab Ide Plugin

    I installed from the sources, I never install binaries. I don't even have a Delphi like those precompiled versions. I don't even get it why are they different, nevermind.
  16. Attila Kovacs

    Ctrl Tab Ide Plugin

    It's indeed promising, but there are several issues. At least with the github version, I'm not sure if it's the latest version though.
  17. Attila Kovacs

    ctrl+b on the welcome page

    @Lars Fosdal Hmm, okay, then something strange happening here. As I wrote, ctrl-b (bookmark or what) pressed on the welcome page.
  18. google: site:.jp delphi debug project1.exe or something like that. however no luck with site:.fr. they must be awesome coder ๐Ÿ˜‰
  19. This won't help you, am I right? ๐Ÿ˜‰ Maybe this:
  20. Attila Kovacs

    Load form icon while using styles

    total pointless debate, doesn't matter a thing which one you call, and the implementation won't change in the next 40 years, nor the bug will be fixed.
  21. Attila Kovacs

    TMemoryStream.Write

    Ok, no "for" loop, no "xor" etc.. which hides implementation details on Char, and reverted back to text=LineBreak delivers 1 empty string for compatibility reasons (original TString / .Split(), etc...) procedure TStringList.SetTextStr(const Value: string); var P, P2, fc, Start, LineBreakEnd: PChar; s: string; LineBreakLen: integer; LLineBreak: PChar; begin BeginUpdate; try Clear; P := Pointer(Value); if P <> nil then begin LLineBreak := PChar(LineBreak); LineBreakLen := Length(LLineBreak); if LineBreakLen > 0 then begin LineBreakEnd := LLineBreak + LineBreakLen; fc := LLineBreak; Start := P; while P^ <> #0 do begin while (P^ <> fc^) and (P^ <> #0) do Inc(P); if P^ <> #0 then begin P2 := P + 1; Inc(fc); while fc^ <> #0 do begin if P2^ <> fc^ then Break; Inc(P2); Inc(fc) end; if fc = LineBreakEnd then begin SetString(s, Start, P - Start); Add(s); P := P2; Start := P; end else Inc(P); fc := LLineBreak; end; end; if P > Start then begin SetString(s, Start, P - Start); Add(s); end; end else Add(Value); end; finally EndUpdate; end; end;
  22. Attila Kovacs

    TMemoryStream.Write

    @Mahdi Safsafi Can you give me a test case for the incorrect handling of the trailing? This would be important to know. In the meanwhile I made a non-recursive version as Stefan pointed out it should be faster, I knew it, but for some reason I decided to make it with a recursive nested procedure. And as the RTL version was unable to handle the mentioned file, with a faulty LineBreak (#10#10#13), and my version worked like a charm I did not go for any further optimization. And by the way, thus did it became a good example for OoOE. This is the new last one: Stefan means, I could achieve even better results without the "for", but I could not. It's beyond me. I rolled out the first contact to the LineBreak and therefor the "for" is not reached too often. I think I reached the max effort I can put into this (time/pay off). It's also faster than yours by the way, and your implementation fails on 7 test-cases of mine. procedure TStringList.SetTextStr(const Value: string); var P, fc, Start: PChar; b: boolean; i: integer; s: string; LineBreakLen: integer; LLineBreak: string; begin if LineBreak = #13#10 then inherited else begin BeginUpdate; try Clear; P := Pointer(Value); if P <> nil then begin LLineBreak := LineBreak; LineBreakLen := Length(LLineBreak); if LineBreakLen > 0 then begin fc := Pointer(LineBreak); Start := P; while P^ <> #0 do begin while (P^ <> fc^) and (P^ <> #0) do Inc(P); if P^ <> #0 then begin b := True; for i := 1 to LineBreakLen - 1 do if (P + i)^ <> (fc + i)^ then begin b := False; Break; end; if b then begin SetString(s, Start, P - Start); Add(s); Inc(P, LineBreakLen); Start := P; end else Inc(P); end; end; if P > Start then begin SetString(s, Start, P - Start); Add(s); end; end else Add(Value); end; finally EndUpdate; end; end; end;
  23. Attila Kovacs

    TMemoryStream.Write

    I was struggling to write this down or not, poor dummzeuch's thread is hijacked as hell, but I can't stand, sorry. I cached the property LineBreak as Stefan suggested, but I could not P2 and LineBreakLen. Brain overflow. (less opcode, less stack usage) Then, I inverted the "if" in the middle, because the most likely branch is not to have a LineBreak at the current position in the string. (theoretically OoOE) Then I put Exit()'s instead of "Result :=" which resulted in 2 more exit points, which allows the compiler to use more registers instead of the stack. (less opcode, more register and less stack usage) Finally it went down to around 265ms (from 300), and I got a code which is far from any straightforward thinking and looks ugly and harder to understand. Maybe the last Exit() is unnecessary but this is not the point. It's interesting, how tiny things can affect the speed. Originally I was starting from 320ms and it was a replacement for the RTL which was using 10's of seconds to do the same thing. But I barely think that anybody could/would get used to it to write "if then else begin <actual code> end;" just because the most likely branch would be to do nothing. function IsBreak(AChar: PChar; ALineBreakPos: integer = 1): boolean; begin if AChar^ <> #0 then begin P2 := AChar; if (AChar^ <> LLineBreak[ALineBreakPos]) or (ALineBreakPos > LineBreakLen) then Exit(False) else Exit(IsBreak(AChar + 1, ALineBreakPos + 1)); end else Exit(True); end;
  24. Attila Kovacs

    Your RAD Studio 10.4 Sydney issues

    @A.M. Hoornweg I have recently "installed" DUnitX back to the IDE by adding its bpl to the packages (install packages) from \Users\All Users\Documents\Embarcadero\Studio\xx.0\Bpl However, not 10.4 and not because of the patch tool
  25. Attila Kovacs

    Again with memory leaks and FastMM4

    maybe a non-graceful exit? maybe there were running some indy threads in the background? the leaked string is in the dump, reference count: 1, string: "/api/login" btw. debugging session could also lead to leaked strings.
ร—