在展开过程中,fixpoint已经是一个集合和管道的组合。它的expand_term/2只是一步term_expansion/2条款的传递闭包。但这仅适用于进入术语时,在我看来,我们在重新组装术语时也需要一些东西。
在罕见情况下,这种传递闭包甚至需要(==)/2检查,就像一些Prolog系统中发现的那样。最有可能的是,如果没有任何term_expansions/2做任何事情,它可以简单地停止。因此,基本上我们没有(==)/2检查:
expand_term(X, Y) :- term_expansion(X, H), !, expand_term(H, Y).
expand_term(.. ..) :-
但是我希望看到的是在扩展框架中添加一种简化框架。因此,当我们进入元谓词并返回时,应调用简化钩子。
这符合某些术语重写理论,其认为:复合体的正常形式(nf)是其部分的正常形式的函数。扩展框架因此不会处理正常形式,只会提供谓词的重新定义,但简化框架将处理正常形式工作。
nf(f(t_1,..,t_n)) --> f'(nf(t_1),..nf(t_n))
因此,简化钩子将采取
f(nf(t_1), .., nf(t_n))
,假设在下降到元谓词时,expand_term已经为元参数产生了
nf(t_1)
..
nf(t_n)
,然后简单地将
f(nf(t_1), .., nf(t_n))
提供给简化器。
然后,简化器将返回
f'(nf(t_1), .., nf(t_n))
,即执行其工作并返回一个简化的形式,基于参数已经被简化的假设。这样的简化器可以非常强大。Jekejeke Prolog在扩展之后提供这样的阶段。
Jekejeke Prolog的简化器及其集成到扩展框架中是开源的,可以在
这里和
这里找到。例如,它用于重新排序连接,以下是此目的的示例规则:
sys_goal_simplification(( ( A, B), C), J) :-
sys_simplify_goal(( B, C), H),
sys_simplify_goal(( A, H), J).
Example:
(((a, b), c), d) --> (a, (b, (c, d)))
Jekejeke Prolog简化器非常高效,因为它可以假设已经接收到了规范化的术语。它不会不必要地重复整个给定术语的模式匹配。
但是,为了编写简化规则,它需要一些重写系统的常见实践。每当构造新术语时,简化规则应该调用简化。
在上面的示例中,这是两个sys_simplify_goal/2调用,例如,我们不能仅返回一个带有(B,C)的新术语,就像扩展规则所做的那样。由于(B,C)不是sys_goal_simplification/2的规范化参数的一部分,所以我们必须先对其进行规范化。
但是,由于简化器框架与扩展框架交织在一起,我怀疑它是否可以称为工作流架构。没有特定的流向,结果更像乒乓球。尽管如此,简化框架可以以模块化的方式使用。
Jekejeke Prolog简化器也用于前向链接子句重写。在那里,它从一个前向子句生成多个增量计算子句。
再见