Doing your own regular expression matching

Posted by Nick Gammon on Thu 23 May 2002 11:51 PM — 3 posts, 19,284 views.

Australia Forum Administrator #0
I got this tip during the MUD Meet and Greet. You can do your own regular expression parsing inside a script (for example, you might want to match on more than 9 wildcards).

From what I can see of the syntax, the regular expressions are very similar to the ones used by MUSHclient internally.

Below is an example - you can try that in an "immediate" window.


Function RegExpTest(patrn, strng)
  Dim regEx, Match, Matches		' Create variable.
  Set regEx = New RegExp			' Create a regular expression.
  regEx.Pattern = patrn			' Set pattern.
  regEx.IgnoreCase = True			' Set case insensitivity.
  regEx.Global = True			' Set global applicability.
  Set Matches = regEx.Execute(strng)	' Execute search.
  For Each Match in Matches		' Iterate Matches collection.
    RetStr = RetStr & "Match found at position "
    RetStr = RetStr & Match.FirstIndex & ". Match Value is '"
    RetStr = RetStr & Match.Value & "'." & vbCRLF
  Next
  RegExpTest = RetStr
End Function

MsgBox(RegExpTest("is.", "IS1 is2 IS3 is4"))



The person I was talking to was using them inside a trigger, taking the actual trigger text to re-evaluate the regular expression inside the trigger, like this ...


sub MyTrigger (sName, sLine, wildcards)

Set regEx = New RegExp

' get trigger match text
regEx.Pattern = world.GetTriggerInfo(sName, 1)

Set Matches = regEx.Execute(sLine)

For Each match in Matches
'
'  do something here
'
Next

end sub


There are also "Test" and "Replace" methods.

Test just tests to see if the regular expression matched or not.

Replace replaces one with another.

For example, here is how you can replace one string with another ...


Function ReplaceTest(patrn, replStr)
  Dim regEx, str1					' Create variables.
  str1 = "The quick brown fox jumped over the lazy dog."
  Set regEx = New RegExp				' Create regular expression.
  regEx.Pattern = patrn				' Set pattern.
  regEx.IgnoreCase = True				' Make case insensitive.
  ReplaceTest = regEx.Replace(str1, replStr)	' Make replacement.
End Function

MsgBox(ReplaceTest("fox", "cat"))		' Replace 'fox' with 'cat'.
Amended on Thu 23 May 2002 11:53 PM by Nick Gammon
Australia Forum Administrator #1
See Regular Expression (RegExp) Object for more details.
#2
Here's an another example of using Regular Expressions inside of VBScript.

The only reason I really see this being useful is if you either have more than MushClient's limit of 9 regular expression to match, or if you have a complex line you would rather catch simply with MushClient's trigger and parse more heavily in script.

As you can see from the code I had a need to match on 13 items; however, didn't like the idea of maintaining two seperate triggers for it.

I've cleaned up the code a little for this outline and based it only on one hit point bar that I am capable of seeing. In reality, it can change at times, and I use 4 seperate triggers with specific names in order to detect how to parse the data correctly when some item(s) are missing.


' Output to match
' HP: 500/500 SP: 200/200 W: 300/500(200) L: 100% P: 3/100% A: 30 T: perfect G: 100

' Trigger:
'  <trigger
'   enabled="y"
'   match="HP: ([0-9]+)/([0-9]+) SP: ([-]*[0-9]+)/([0-9]+) W: ([0-9]+)/([0-9]+)\(([0-9]+)\) L: ([0-9]+)\% P: ([0-9])/([0-9]+)\% A: ([0-9]+) T: ([a-z]+) G: ([0-9]+)$"
'   name="catch_hp"
'   regexp="y"
'   script="catch_hp_bar"
'   sequence="91"
'  >
'  </trigger>


Dim hp_hp, hp_hp_max
Dim hp_sp, hp_sp_max
Dim hp_water, hp_water_max, hp_water_recycle
Dim hp_limberness
Dim hp_poison, hp_reset
Dim hp_ammo
Dim hp_target
Dim hp_gxp

Sub catch_hp_bar(ByVal strName, ByVal strLine, ByVal astrParam())
  Dim regEx, Matches, Match

  Set regEx =     New RegExp
  regEx.Pattern = world.GetTriggerInfo(strName, 1)
  Set Matches =   regEx.Execute(strLine)
  Set Match =     Matches(0)

  Set regEx =   Nothing
  Set Matches = Nothing

  hp_hp =            CInt(Match.SubMatches(0))
  hp_hp_max =        CInt(Match.SubMatches(1))
  hp_sp =            CInt(Match.SubMatches(2))
  hp_sp_max =        CInt(Match.SubMatches(3))
  hp_water =         CInt(Match.SubMatches(4))
  hp_water_max =     CInt(Match.SubMatches(5))
  hp_water_recycle = CInt(Match.SubMatches(6))
  hp_limberness =    CInt(Match.SubMatches(7))
  hp_poison =        CInt(Match.SubMatches(8))
  hp_reset =         CInt(Match.SubMatches(9))
  hp_ammo =          CInt(Match.SubMatches(10))
  hp_target =        Match.SubMatches(11)
  hp_gxp =           CInt(Match.SubMatches(12))

  Set Match = Nothing

' process data

End Sub