Einzelnen Beitrag anzeigen

Benutzerbild von himitsu
himitsu

Registriert seit: 11. Okt 2003
Ort: Elbflorenz
44.184 Beiträge
 
Delphi 12 Athens
 

(Teil)String in anderem String suchen/zählen

  Alt 9. Aug 2005, 19:35
Was Pos und PosEx machen, wird bestimmt bekannt sein.
Da aber speziell PosEx nicht überall verfügbar ist,
sind diese hier auch mit enthalten. (damit Lucke es endlich mal findet)
Pos liegt der Vollständigkeit halber bei.

CountString zählt dagegen alle Vorkommen des gesuchten SubStrings,
allerdings maximal nur 65.535 (bei mehr wird abgebrochen - es gibt also keinen Überlauf).

Und als Bonus ist alles auch nochmal als UnicodeVersion vorhanden ^^

Delphi-Quellcode:
  Function _Pos (Const SubStr, S: AnsiString): LongInt;
  Function _Pos (Const SubStr, S: WideString): LongInt;
  Function _PosEx (Const SubStr, S: AnsiString; Offset: LongInt = 1): LongInt;
  Function _PosEx (Const SubStr, S: WideString; Offset: LongInt = 1): LongInt;
  Function CountString(Const SubStr, S: AnsiString): Word;
  Function CountString(Const SubStr, S: WideString): Word;
Delphi-Quellcode:
// © 1997-2005 by FNS Enterprize's™
// 2003-2005 by himitsu @ Delphi-PRAXiS

  Function _Pos(Const SubStr, S: AnsiString): LongInt;
    ASM
      PUSH ESI
      PUSH EDI
      PUSH EBX
      TEST &SubStr, &SubStr
      JE @Exit
      TEST &S, &S
      JE @Exit0
      MOV ESI, &SubStr
      MOV EDI, &S
      PUSH EDI
      MOV ECX, [EDI - 4]
      MOV EDX, [ESI - 4]
      DEC EDX
      JS @Fail
      MOV AL, [ESI]
      INC ESI
      SUB ECX, EDX
      JLE @Fail

      @Loop:
      REPNE SCASB
      JNE @Fail
      MOV EBX, ECX
      PUSH ESI
      PUSH EDI
      MOV ECX, EDX
      REPE CMPSB
      POP EDI
      POP ESI
      JE @Found
      MOV ECX, EBX
      JMP @Loop

      @Fail:
      POP EDX

      @Exit0:
      XOR EAX, EAX
      JMP @Exit

      @Found:
      POP EDX
      MOV EAX, EDI
      SUB EAX, EDX

      @Exit:
      POP EBX
      POP EDI
      POP ESI
    End;

  Function _Pos(Const SubStr, S: WideString): LongInt;
    ASM
      PUSH ESI
      PUSH EDI
      PUSH EBX
      TEST &SubStr, &SubStr
      JE @Exit
      TEST &S, &S
      JE @Exit0
      MOV ESI, &SubStr
      MOV EDI, &S
      PUSH EDI
      MOV ECX, [EDI - 4]
      SAL EAX, 1
      MOV EDX, [ESI - 4]
      SAL EDX, 1
      DEC EDX
      JS @Fail
      MOV AX, [ESI]
      ADD ESI, 2
      SUB ECX, EDX
      JLE @Fail

      @Loop:
      REPNE SCASW
      JNE @Fail
      MOV EBX, ECX
      PUSH ESI
      PUSH EDI
      MOV ECX, EDX
      REPE CMPSW
      POP EDI
      POP ESI
      JE @Found
      MOV ECX, EBX
      JMP @Loop

      @Fail:
      POP EDX

      @Exit0:
      XOR EAX, EAX
      JMP @Exit

      @Found:
      POP EDX
      MOV EAX, EDI
      SUB EAX, EDX
      SHR EAX, 1

      @Exit:
      POP EBX
      POP EDI
      POP ESI
    End;

  Function _PosEx(Const SubStr, S: AnsiString; Offset: LongInt = 1): LongInt;
    ASM
      PUSH ESI
      PUSH EDI
      PUSH EBX
      TEST &SubStr, &SubStr
      JE @Exit
      TEST &S, &S
      JE @Exit0
      TEST &Offset, &Offset
      JG @POff
      MOV &Offset, 1
      @POff:
      MOV ESI, &SubStr
      MOV EDI, &S
      PUSH EDI
      MOV EAX, &Offset
      DEC EAX
      MOV ECX, [EDI - 4]
      MOV EDX, [ESI - 4]
      DEC EDX
      JS @Fail
      SUB ECX, EAX
      ADD EDI, EAX
      MOV AL, [ESI]
      INC ESI
      SUB ECX, EDX
      JLE @Fail

      @Loop:
      REPNE SCASB
      JNE @Fail
      MOV EBX, ECX
      PUSH ESI
      PUSH EDI
      MOV ECX, EDX
      REPE CMPSB
      POP EDI
      POP ESI
      JE @Found
      MOV ECX, EBX
      JMP @Loop

      @Fail:
      POP EDX

      @Exit0:
      XOR EAX, EAX
      JMP @Exit

      @Found:
      POP EDX
      MOV EAX, EDI
      SUB EAX, EDX

      @Exit:
      POP EBX
      POP EDI
      POP ESI
    End;

  Function _PosEx(Const SubStr, S: WideString; Offset: LongInt = 1): LongInt;
    ASM
      PUSH ESI
      PUSH EDI
      PUSH EBX
      TEST &SubStr, &SubStr
      JE @Exit
      TEST &S, &S
      JE @Exit0
      TEST &Offset, &Offset
      JG @POff
      MOV &Offset, 1
      @POff:
      MOV ESI, &SubStr
      MOV EDI, &S
      PUSH EDI
      PUSH &Offset
      MOV ECX, [EDI - 4]
      SAL ECX, 1
      MOV EDX, [ESI - 4]
      SAL EDX, 1
      POP EAX
      DEC EAX
      DEC EDX
      JS @Fail
      SUB ECX, EAX
      ADD EDI, EAX
      ADD EDI, EAX
      MOV AX, [ESI]
      ADD ESI, 2
      SUB ECX, EDX
      JLE @Fail

      @Loop:
      REPNE SCASW
      JNE @Fail
      MOV EBX, ECX
      PUSH ESI
      PUSH EDI
      MOV ECX, EDX
      REPE CMPSW
      POP EDI
      POP ESI
      JE @Found
      MOV ECX, EBX
      JMP @Loop

      @Fail:
      POP EDX

      @Exit0:
      XOR EAX, EAX
      JMP @Exit

      @Found:
      POP EDX
      MOV EAX, EDI
      SUB EAX, EDX
      SHR EAX, 1

      @Exit:
      POP EBX
      POP EDI
      POP ESI
    End;

  Function CountString(Const SubStr, S: AnsiString): Word;
    ASM
      PUSH ESI
      PUSH EDI
      PUSH EBX
      TEST &SubStr, &SubStr
      JE @Exit
      TEST &S, &S
      JE @Exit0
      MOV ESI, &SubStr
      MOV EDI, &S
      PUSH EDI
      MOV ECX, [EDI - 4]
      MOV EDX, [ESI - 4]
      DEC EDX
      JS @Fail
      XOR EAX, EAX
      MOV AL, [ESI]
      INC ESI
      SUB ECX, EDX
      JLE @Fail

      @Loop:
      REPNE SCASB
      JNE @Ready
      MOV EBX, ECX
      PUSH ESI
      PUSH EDI
      MOV ECX, EDX
      REPE CMPSB
      POP EDI
      POP ESI
      JNE @noInc
      CMP EAX, $FFFF0000
      JAE @Ready
      ADD EAX, $00010000
      @noInc:
      MOV ECX, EBX
      JMP @Loop

      @Fail:
      POP EDX

      @Exit0:
      XOR EAX, EAX
      JMP @Exit

      @Ready:
      POP EDX
      SHR EAX, 16

      @Exit:
      POP EBX
      POP EDI
      POP ESI
    End;

  Function CountString(Const SubStr, S: WideString): Word;
    ASM
      PUSH ESI
      PUSH EDI
      PUSH EBX
      TEST &SubStr, &SubStr
      JE @Exit
      TEST &S, &S
      JE @Exit0
      MOV ESI, &SubStr
      MOV EDI, &S
      PUSH EDI
      MOV ECX, [EDI - 4]
      SAL ECX, 1
      MOV EDX, [ESI - 4]
      SAL EDX, 1
      DEC EDX
      JS @Fail
      XOR EAX, EAX
      MOV AX, [ESI]
      ADD ESI, 2
      SUB ECX, EDX
      JLE @Fail

      @Loop:
      REPNE SCASW
      JNE @Ready
      MOV EBX, ECX
      PUSH ESI
      PUSH EDI
      MOV ECX, EDX
      REPE CMPSW
      POP EDI
      POP ESI
      JNE @noInc
      CMP EAX, $FFFF0000
      JAE @Ready
      ADD EAX, $00010000
      @noInc:
      MOV ECX, EBX
      JMP @Loop

      @Fail:
      POP EDX

      @Exit0:
      XOR EAX, EAX
      JMP @Exit

      @Ready:
      POP EDX
      SHR EAX, 16

      @Exit:
      POP EBX
      POP EDI
      POP ESI
    End;
Natürlich auch in himi's Hier im Forum suchenUCC enthalten. (FNSEnt.UCS.STRINGS = FNS_Strings.pas)

[edit=SirThornberry] Mfg, SirThornberry[/edit]
$2B or not $2B
  Mit Zitat antworten Zitat