Jump to content

_StringMatch - Search in Strings by logical patterns


minxomat
 Share

Recommended Posts

Example and explaination in the script:

#include <Array.au3>

$sInput = 'Ashley R., Harris and Maxwell are going to the lake.'

$sQuery = '((Ashley and R.) and (lake and not mountain)) and Harris and "and Maxwell"'
; -> There is a Person named Ashley
; -> Ashleys (or someones) surname is R.
; -> There is a lake, but no mountain
; -> There is a Person named Harris
; -> Maxwell should be the last person mentioned in this sentence

ConsoleWrite("-> " & _StringMatch($sQuery, $sInput) & @LF)

; #FUNCTION# ====================================================================================================================
; Name ..........: _StringMatch
; Description ...: Returns wether the search pattern matches the given string.
;                  Boolean Operators, Brackets and Quotes can be used:
;                  Available OPs: and or not xor
;                  Brackets and even nested Brackets can be used (causes recursion).
;                  Use quotes to search for strings containing spaces
; Syntax ........: _StringMatch($sSearch, $sString)
; Parameters ....: $sSearch             - The search pattern.
;                  $sString             - A string value.
; Return values .: true or false
; Author ........: minx
; Example .......: s. above
; ===============================================================================================================================
Func _StringMatch($sSearch, $sString)
    If $sSearch = "" Then Return SetError(1)
    Local $j[1], $b = 1
    $s = _StringInStrRev($sSearch, "(")
    While 1
        If $s > 0 Then
            $f = StringInStr($sSearch, ")", 0, 1, $s)
            If $f > 0 Then $sSearch = StringMid($sSearch, 1, $s - 1) & _StringMatch(StringMid($sSearch, $s + 1, $f - $s - 1), $sString) & StringMid($sSearch, $f + 1)
        EndIf
        $s = _StringInStrRev($sSearch, "(")
        If Not ($s > 0 And $f > 0) Then ExitLoop
    WEnd
    $i = StringSplit($sSearch, " ", 3)
    If StringInStr($sSearch, """", 0, 1, 1) Then
        For $a = UBound($i)-1 To 0 Step -1
            If StringRight($i[$a], 1) = """" And StringLeft($i[$a], 1) <> """" Then
                $i[$a - 1] &= " " & $i[$a]
                $i[$a] = ""
            EndIf
            If StringRight($i[$a], 1) = """" And StringLeft($i[$a], 1) = """" And StringLen($i[$a]) > 1 Then $i[$a] = "!" & StringMid($i[$a], 2, StringLen($i[$a]) - 2)
        Next
        For $a = 0 To UBound($i)-1
            If $i[$a] <> "" Then
                ReDim $j[$b]
                $j[$b - 1] = $i[$a]
                $b += 1
            EndIf
        Next
        $i = $j
    EndIf
    For $a = 0 To UBound($i)-1
        Switch StringUpper($i[$a])
        Case "AND"
            $i[$a] = "AND"
        Case "OR"
            $i[$a] = "OR"
        Case "NOT"
            $i[$a] = "NOT"
        Case "XOR"
            $i[$a] = "XOR"
        Case "TRUE"
            $i[$a] = "true"
        Case "FALSE"
            $i[$a] = "false"
        Case Else
            If StringLeft($i[$a], 1) = "!" Then $i[$a] = StringMid($i[$a], 2)
            $i[$a] = StringLower(StringInStr($sString, $i[$a], 0, 1, 1) <> 0)
        EndSwitch
    Next
    $sSearch = _ArrayToString($i, " ")
    While 1
        If StringInStr($sSearch, "NOT", 0, 1, 1) <> 0 Then
            $sSearch = StringReplace($sSearch, "NOT false", "true")
            $sSearch = StringReplace($sSearch, "NOT true", "false")
        EndIf

        If StringInStr($sSearch, "OR", 0, 1, 1) <> 0 Then
            $sSearch = StringReplace($sSearch, "false OR false", "false")
            $sSearch = StringReplace($sSearch, "true OR false", "true")
            $sSearch = StringReplace($sSearch, "false OR true", "true")
            $sSearch = StringReplace($sSearch, "true OR true", "true")
        EndIf

        If StringInStr($sSearch, "XOR", 0, 1, 1) <> 0 Then
            $sSearch = StringReplace($sSearch, "false XOR false", "false")
            $sSearch = StringReplace($sSearch, "true XOR false", "true")
            $sSearch = StringReplace($sSearch, "false XOR true", "true")
            $sSearch = StringReplace($sSearch, "true XOR true", "false")
        EndIf

        If StringInStr($sSearch, "AND", 0, 1, 1) <> "0" Then
            $sSearch = StringReplace($sSearch, "false AND false", "false")
            $sSearch = StringReplace($sSearch, "true AND false", "false")
            $sSearch = StringReplace($sSearch, "false AND true", "false")
            $sSearch = StringReplace($sSearch, "true AND true", "true")
        EndIf

        If StringInStr($sSearch, " ", 0, 1, 1) Then
            $sSearch = StringReplace($sSearch, "true true", "true")
            $sSearch = StringReplace($sSearch, "false true", "true")
            $sSearch = StringReplace($sSearch, "true false", "true")
            $sSearch = StringReplace($sSearch, "false false", "false")
            If StringInStr($sSearch, " ", 0, 1, 1) Then
                $sSearch &= " false"
                ContinueLoop
            EndIf
        EndIf
        ExitLoop
    WEnd
    Return $sSearch
EndFunc

Func _StringInStrRev($sString, $sSearch)
    $iPtr = StringLen($sSearch)
    For $nPos = StringLen($sString) - $iPtr To 1 Step -1
        If StringMid($sString, $nPos, $iPtr) = $sSearch Then Return $nPos
    Next
    Return 0
EndFunc

I will answer every single PM, and you are free to ask anything anytime.

Link to comment
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
 Share

  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...