Thread: [Solved] Find Challenge
View Single Post
 
Old 01-07-2025, 05:20 AM
gmaxey gmaxey is offline Windows 10 Office 2019
Expert
 
Join Date: May 2010
Location: Brasstown, NC
Posts: 1,601
gmaxey is just really nicegmaxey is just really nicegmaxey is just really nicegmaxey is just really nicegmaxey is just really nice
Default

Batman1


I consider myself schooled. Thank you for the lesson. I was reading up on look ahead and look behind assertions last night before reading your reply this morning. I fully understand your pattern now and this my code with my own notes.

Code:
Sub RegExMethod()
Dim RegEx As Object, Matches As Object, Match As Object
Dim oRng As Range
  Set RegEx = CreateObject("VBScript.RegExp")
  With RegEx
    .Global = True
    .Pattern = "(?=\d{0,3}2)\d{4,5}"
    'Positive lookahead.
    'y = (?=\d{0,3}2) x = \d{4,5}
    'Match second part x only if first part y matches.
    'y matches 2, #2, ##2 or ###2
    'x matches 2####, #2###, ##2##, and ###2# or 2###, #2##, ##2# and ###2
  End With
  Set Matches = RegEx.Execute(ActiveDocument.Range.Text)
  For Each Match In Matches
    ActiveDocument.Range(Match.FirstIndex, Match.FirstIndex + Match.Length).HighlightColorIndex = wdBrightGreen
  Next
lbl_Exit:
  Exit Sub
End Sub

Now, in reading about the look ahead and look behind assertions earlier, I came across an example:
Pattern = "(?<=Tom|Jack)Sprat"
'Look behind assertions. - matches "x" only if "x" is preceded by "y". For example, (?<=Jack|Tom)Sprat matches "Sprat" only if it is preceded by "Tom" or "Jack." However, neither "Jack" nor "Tom" is part of the match results.


Sample text:

Jack Sprat, Johnny Sprat, Tom Sprat, Mary Sprat and Bill Sprat.



I learned (after some frustration) that look behind assertions are unfortunately not supported in VBA. So, how do achieve the same results with VBA? Here is a look ahead that comes close, but unlike the look behind described above, it returns both parts y and x.



Code:
Sub RegEx()
Dim RegEx As Object, Matches As Object, Match As Object
Dim oRng As Range
  Set RegEx = CreateObject("VBScript.RegExp")
  With RegEx
    .Global = True
    .Pattern = "(?=Tom|Jack)\S+ Sprat"
  End With
  Set Matches = RegEx.Execute(ActiveDocument.Range.Text)
  For Each Match In Matches
    'Returns Jack Sprat and Tom Sprat (Not just Sprat like lookback)
    ActiveDocument.Range(Match.FirstIndex, Match.FirstIndex + Match.Length).Select
  Next
lbl_Exit:
  Exit Sub
End Sub
__________________
Greg Maxey
Please visit my web site at http://www.gregmaxey.com/
Reply With Quote