Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/regex/20.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Regex 通配符匹配反向查找_Regex_Wildcard_Matching - Fatal编程技术网

Regex 通配符匹配反向查找

Regex 通配符匹配反向查找,regex,wildcard,matching,Regex,Wildcard,Matching,我有一个包含零个或多个通配符(*)的模式列表,这些模式位于其主体的任何位置: bleurgh p0* p*w p*w* *01 *.nowsich.* (dots here are meaningless) 只允许使用通配符(这不是任何类型的完整正则表达式),它们可以出现在模式中的任何位置。只使用通配符的模式是不允许的,而双通配符(***)是毫无意义的,因为它与*相同(但保证有人会尝试)。其中大约有10万到100万个通配符 代码将看到可能匹配的新目标字符串: p01w01 pod01whisk

我有一个包含零个或多个通配符(
*
)的模式列表,这些模式位于其主体的任何位置:

bleurgh
p0*
p*w
p*w*
*01
*.nowsich.* (dots here are meaningless)
只允许使用通配符(这不是任何类型的完整正则表达式),它们可以出现在模式中的任何位置。只使用通配符的模式是不允许的,而双通配符(
***
)是毫无意义的,因为它与
*
相同(但保证有人会尝试)。其中大约有10万到100万个通配符

代码将看到可能匹配的新目标字符串:

p01w01
pod01whiskey02
ppp.nowsich.com
aZL8u4qXfg!LooksLikeRandomGarbageToMe!kx961giRVV
callmeishmael
这些字符串是无界的,但可能少于(比如)32个字符,代码将以每秒两次的顺序看到它们(这是一种低速率的事情)

我正在寻找一种反向查找字符串可能匹配的模式的方法:(这里是输入到输出)

我不受记忆的约束;更快的查找肯定更好

到目前为止,我能想到的最好方法是构建模式组件的有向图,其中每个组件都是
split(“*”,pattern)
的输出,后面的通配符绑定到它们的叶:

        ___   {implied root node} 
       /      /    |           \
[bleurgh]  [p0]   [p]          [] // leading wildcard?
           /      /           /  \
         [w]    [w*]       [01]  [.nowsich.*]
…并在树上执行DFS,选择那些根节点regex与从子树的父节点(一直到根节点)重新编译的模式匹配的子树。我不喜欢这样的想法,
O(log n)
?正则表达式,但数据集不是很大。此外,我相信我必须始终搜索树的“前导通配符”分支,因此可能搜索一对树(一个带前导通配符,一个不带前导通配符)是一种方法

有一些以前的艺术,由于各种原因似乎不适用:

这两者都有自己的限制,与我的不一致


问题是,a)我上面概述的方法有意义吗;b)你有更好的方法吗?

做了一些实际的写作来完成这项工作,以下是我学到的:

  • 这个想法确实有效,但是不要使用树,而是使用trie。当根据模式测试字符串时,它将允许您跳过没有值且只有一个子节点的节点,从而减少需要执行的正则表达式的数量
  • 尾随和前导通配符需要特殊处理,至少在我的情况下是这样(回想一下,在我的情况下,只有通配符--
    *
    --char具有特殊含义。)如果没有前导或尾随通配符,则需要在为模式存储的第一个或最后一个键上包含锚定符。这意味着模式
    *p0*
    p0*
    由树中的两个节点表示。(与叶节点类似——即模式中的最终标记。)
  • 另一个特别针对我的情况的注意事项是:我需要逃避所有对regex有意义但对我没有意义的东西——例如chars
    [
    ]
    {
    }
    ,等等。可以在模式匹配trie中包含这些元素,但必须以不同的方式进行标记
  • 存储要匹配的已编译正则表达式是一种速度提升。在我的例子中,这是用Go编写的,因此我可以为树中的每个节点存储
    regexp.Compile([interstitual pattern])
    的结果
        ___   {implied root node} 
       /      /    |           \
[bleurgh]  [p0]   [p]          [] // leading wildcard?
           /      /           /  \
         [w]    [w*]       [01]  [.nowsich.*]