首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >一种有效的大模式集字符串匹配算法

一种有效的大模式集字符串匹配算法
EN

Stack Overflow用户
提问于 2013-01-31 12:56:24
回答 3查看 2.7K关注 0票数 6

我正在寻找一个高效的算法,能够找到所有匹配特定字符串的模式。模式集可以非常大(超过100,000)和动态(任何时候添加或删除的模式)。模式不一定是标准的regexp,它们可以是regexp的子集,也可以类似于shell模式(即:file-*.txt)。正则表达式子集的解决方案是首选的(如下所述).

FYI:我对基于RegExp.列表的蛮力方法不感兴趣

通过简单的regexp,我指的是一个正则表达式,它支持?*+、字符类[a-z],可能还支持逻辑运算符|

为了澄清我的需要:我希望找到与URL匹配的所有模式:

代码语言:javascript
运行
复制
http://site1.com/12345/topic/news/index.html

响应应该是基于下面设置的模式的这些模式。

代码语言:javascript
运行
复制
http://*.site1.com/*/topic/*
http://*.site1.com/* 
http://*

模式集:

代码语言:javascript
运行
复制
http://*.site1.com/*/topic/*
http://*.site1.com/*/article/*
http://*.site1.com/* 
http://*.site2.com/topic/*
http://*.site2.com/article/*
http://*.site2.com/* 
http://*
EN

回答 3

Stack Overflow用户

发布于 2019-04-13 01:48:25

下面是我们非常成功地使用了一种方法(在这里实施):

添加模式:

对于任何模式,都存在一组字符串必须包含的子字符串,以便有机会与其匹配。把这些元词叫做。例如:

代码语言:javascript
运行
复制
dog*fish -> [dog, fish]
[lfd]og  -> [og]
dog?     -> [dog]

将模式添加到数据结构中时,将其分解为元单词,并将它们存储在符合数据结构的字符串中。维护内部数据结构,将元单词映射回模式词。

运行查询:

给定一个输入字符串,使用您构建的数据结构来获取包含在该字符串中的所有元单词。然后,使用您创建的映射,测试与这些元单词对应的模式。

这很好,因为虽然字符串匹配相当慢,但是您可以缩小实际必须匹配的模式的数量。我们的实现每秒可以针对一组150,000+模式在普通笔记本上执行大约20万次查询。请参阅程序中的台架标记模式来测试这一点。

票数 3
EN

Stack Overflow用户

发布于 2013-01-31 13:40:06

脑海中浮现的一种方法是创建模式的树结构。

示例:http://*将包含所有模式(上面列出)。http://*.site1.com/*将包含所有的site1.com。这可以大大减少需要检查的模式的数量。

此外,您还可以确定哪些模式是相互排斥的,以进一步删除搜索的列表。

所以首先把所有的图案都拿出来,然后创造出它们的树。搜索所有根,以确定哪些分支和节点需要分析。

通过确定哪些分支是互斥的,从而改进算法,因此一旦在给定分支上找到命中,您就会知道哪些分支/节点不需要被访问。

首先,您可能很懒,您的第一个步骤可能是对模式进行排序,并执行简单的下一步模式,其中包含此模式类型逻辑,以确定下一个模式中是否包含" this“。例:if( "http://*.site1.com/*".startsWith("http://*") == true )

您可以在判断一个模式是否确实包含另一个模式方面变得更加复杂,但这将使您开始工作。

为了更好地确定这个问题:

“这个模式包含这个模式吗?”

我相信你需要能够解析正则表达式..。为了理解如何实现这一点,本文似乎是一个很好的起点:解析具有递归下降的正则表达式

票数 2
EN

Stack Overflow用户

发布于 2013-02-01 15:49:28

如果URL集合变化不快,那么您确实应该使用regex引擎来编译它的模式。Java提供了其中之一,但是如果您想知道哪一种模式匹配,则可能并不令人满意。

一种广泛使用的机制来进行这一和确定哪一个匹配,是各种雷克萨斯生成器,例如,FLEX和类似的工具。他们接受相当于每个"lexeme“的正则表达式,并构建一个完整的FSA来识别其中的任何一个,这是非常高效的执行。

您可以在设置更改时调用Flex。如果速度太慢,那么获取一个开源版本的Flex并集成到您的引擎中;它内部构建FSA,这样您就可以直接使用它。(一些工程可能需要)。但是,如果你真的有一个高性能匹配问题,一些工作做得好不会打扰你。

如果URL集合的变化速度超过FLEX生成FSAs (奇数)的速度,那么您就有了一个真正的问题。在这种情况下,您可以通过从左到右扫描"regex“并将您看到的字符/谓词集成到现有的识别树中来构建在线识别树。然后,匹配包括沿着识别树走下,执行各种测试;如果您到达一片叶子,则有匹配,否则就没有匹配。如果做得对,这可能就像灵活生成的自动化一样快,但很可能要大得多。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/14626339

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档