我有一长串n(~50000)行,其公式看起来像这样:
A(1, 2) = 54353
A(1, 2, 3) = 89327
A(1, B(1, 2)) = 8372
A(7, B(1, 3, 5)) = 6311
A(7, B(C(1, 3, 7), 2, C(1, 3), 5)) = 28490
B(A(1, C(5, 3)), 3, 8, D(1, 2)) = 39783
等
这些公式包含文字(即1
,2
,3
,5
等)和函数调用(即A(x, y)
或{{1或者A(x, y, z)
),其中函数的参数也可以是文字或其他(嵌套)函数调用。功能(即B(x, y)
,A
,B
等)是固定的,并且它们中的数量不多(可能是十几个)。
现在我使用完整公式或某些带C
的模式运行查询,这些模式应该作为全局字符,即:
*
基本上,我有两个问题:
如何做 at :事实上,我不知道这里有一个好的基本模式匹配算法。我试图将带有*的表达式转换为正则表达式,它适用于简单的例子,但是唉,对于更复杂的例子来说是失败的,即:
A(1, 2) => [54353]
A(1, *) => [54353, 89327, 8372]
A(*, 3) => [89327]
A(*, B(*)) => [8372, 6311, 28490]
A(*, B(*, 3, *)) => [6311]
我觉得将这些大括号表达式转换为反向抛光表示法然后应用正常的正则表达式方法可能有所帮助,但我不确定。
如何做到快速:任何想法如何比每次查询~50000匹配更快更受欢迎。可以在这里使用某种FSM吗?
答案 0 :(得分:2)
正则表达式是为Regular Languages(最初)设计的,而您正在描述Context Free Language。
您的语言可以通过确定性Push-Down Automata解析。
这个想法类似于FSM,但除此之外,您还有一个stack可以push()
和pop()
元素。
更改FSM中的状态也取决于堆栈的头部。