Hilog术语(即具有任意术语的函子的复合词)仍然被认为是XSB Prolog(或任何其他Prolog)中的强大功能吗?目前有很多XSB项目使用这个特性吗?比如他们中的哪一个?
我问,因为据我所知,高阶编程同样可以使用ISO内置调用/n
具体来说,我想了解XSB是否只是出于历史原因而使用Hilog术语,或者与当前的ISO标准相比,Hilog术语是否具有相当大的优势。
在XSB中,Hilog术语与XSB特有的模块系统紧密相连。XSB有一个基于函子的模块系统。也就是说,在同一作用域中,length(X)
可能属于一个模块,而length(L, N)
可能属于另一个模块。因此,call(length(L), N)
可能指向一个模块,call(length(L, N))
指向另一个模块:
[Patch date: 2013/02/20 06:17:59]
| ?- use_module(basics,length/2).
yes
| ?- length(Xs,2).
Xs = [_h201,_h203]
yes
| ?- call(length(Xs),2).
Xs = [_h217,_h219]
yes
| ?- use_module(inex,length/1).
yes
| ?- length(Xs,2).
Xs = [_h201,_h203]
yes
| ?- call(length(Xs),2).
++Error[XSB/Runtime/P]: [Existence (No module inex exists)] in arg 1 of predicate load
| ?- call(call(length,Xs),2).
Xs = [_h228,_h230];
可能在这种情况下,call/N
和Hilog术语之间存在差异。然而,到目前为止,我还没有找到。
历史上,Hilog术语是1987-1989年引入的。在那个时间点上,call/N
已经作为内置在NU和library(call)
在Quintus Prolog中存在,只有粗略的文档。它是由理查德·奥基夫在1984年提出的。另一方面,Hilog的作者显然不知道call/N
,如Weidong Chen, Michael Kifer, David Scott Warren: Hilog: A First-Order的第1101页所示高阶逻辑编程结构的语义。NACLP1989. 1090 - 1114。麻省理工学院出版社。
现在,这可以用…泛型传递闭包也可以在Prolog中定义:
closure(R, X, Y) :- C =.. [R, X, Y], call(C). closure(R, X, Y) :- C =.. [R, X, Z], call(C), closure(R, Z, Y).
然而,与HiLog(参见2.1节)相比,这显然是不优雅的,因为这既涉及到从列表中构造一个项,又涉及到使用&;call&;将该项反映到原子公式中。这个例子的要点是,Prolog中缺乏高阶结构的理论基础导致了语法的模糊,这部分解释了为什么涉及这些结构的Prolog程序是出了名的难以理解。
call/N
来完成,像这样:
closure(R, X, Y) :- call(R, X, Y).
closure(R, X, Y) :- call(R, X, Z), closure(R, Z, Y).
这比(=..)/2
-版本更通用,因为R
不再局限于作为一个原子。说句题外话,我更喜欢这样写:
closure(R_2, X0,X) :- call(R_2, X0,X1), closure0(R_2, X1,X).
closure0(_R_2, X,X).
closure0(R_2, X0,X) :- call(R_2, X0,X1), closure0(R_2, X1,X).
HiLog允许以下目标:
foo(X(a, Y(b))).
和ISO Prolog则没有。在ISO Prolog中,你必须写
foo(T), T=..[X, a, R], R=..[Y, b].