我试图在包含问号通配符的更大的字符串中找到文本子字符串的位置。这个大字符串是不精确的OCR软件的结果,它包含通配符,因为它可以知道那里有一个字符,但无法识别是哪个字符。
这是我想要完成的一个过于简化的例子。
Dim resultIndex As Integer = -1
Dim LargeOcrText As String = "fAsD ?GjSDFpG HjDYA?C JLgD FHaYsV MKiI?oL XgXj?GN sHVKgG?"
Dim searchText As String = "ABC"
If searchText Like LargeOcrText Then resultIndex = LargeOcrText.IndexOf(searchText)
这应该返回resultIndex = 18,但它不起作用,即使我使用searchText = "*ABC*"代替。我几乎可以肯定,有一些方法可以使用正则表达式来进行Like比较,但我对它们不太熟悉,即使这样,我也完全不知道如何获得子字符串的索引。
编辑:要清楚,我知道既不喜欢也不IndexOf支持我想做的事情。这正是我的问题所在。我正在寻找一些其他的方式来编码它,做工作。
在您的搜索模式中,将每个字母替换为[<that letter>?]
并将其提供给Regex:
Dim resultIndex As Integer = -1
Dim LargeOcrText As String = "fAsD ?GjSDFpG HjDYA?C JLgD FHaYsV MKiI?oL XgXj?GN sHVKgG?"
Dim searchText As String = "[A?][B?][C?]"
With Regex.Match(LargeOcrText, searchText)
If .Success Then resultIndex = .Index
End With
除了GSerg的回答,可以自动生成模式从ABC
[A?][B?][C?]
。
下面是一个工作代码示例。
Imports System.Linq
Imports System.Text.RegularExpressions
Module Module1
Sub Main()
Dim largeOcrText As String = "fAsD ?GjSDFpG HjDYA?C JLgD FHaYsV MKiI?oL XgXj?GN sHVKgG?"
Dim searchText As String = "ABC"
Dim index As Integer = GetOcrIndex(largeOcrText, searchText)
Debug.WriteLine($"Index = {index}")
End Sub
Private Function GetOcrIndex(haystack As String, needle As String) As Integer
Dim pattern As String = BuildPattern(needle)
Debug.WriteLine($"Pattern = {pattern}")
Dim match As Match = Regex.Match(haystack, pattern, RegexOptions.IgnoreCase)
Return If(match.Success, match.Index, -1)
End Function
Private Function BuildPattern(needle As String) As String
Return String.Concat(needle.SelectMany(AddressOf AddWildcard))
End Function
Private Function AddWildcard(c As Char) As String
Return $"[{Regex.Escape(c)}?]"
End Function
End Module
输出:
Pattern = [A?][B?][C?]
Index = 18