Prolog 使用forall/2扩展序言子句
我用它来转换编译器中的一些Prolog子句。我需要将每个子句的开头替换为其主体,但是Prolog 使用forall/2扩展序言子句,prolog,metaprogramming,swi-prolog,Prolog,Metaprogramming,Swi Prolog,我用它来转换编译器中的一些Prolog子句。我需要将每个子句的开头替换为其主体,但是clause/2有时不能按照最初编写的方式扩展子句 这里,子句/2将演示(A,B)扩展为\+(调用(A),\+call(B)),而不是扩展其原始定义: :- use_module(prolog_to_minizinc). :- initialization(main). main :- writeln(forall(A,B)), clause(demo(A,B),Clause)
clause/2
有时不能按照最初编写的方式扩展子句
这里,子句/2
将演示(A,B)
扩展为\+(调用(A),\+call(B))
,而不是扩展其原始定义:
:- use_module(prolog_to_minizinc).
:- initialization(main).
main :-
writeln(forall(A,B)),
clause(demo(A,B),Clause),
writeln(Clause).
demo(A,B) :-
forall(A,B).
是否有另一种方法来扩展子句,而不修改包含
forall/2
的子句?对forall/2
目标进行不必要的扩展是由于启动时SWI Prolog加载库(应用宏)
。此库为forall/2
和其他谓词提供扩展代码。查找如何加载库(apply_macros)
并非易事,因为在~/.config/swi prolog/init.pl
文件中将verbose_autoload
标志设置为true
,不会打印启动时自动加载的所有库。在我的笔记本电脑上,使用当前的devel-git版本的SWI-Prolog(8.1.21-82-ge6e1d5376-DIRTY
):
文件editline.pl
提供了默认值方便的命令行历史记录和其他服务。但是,如果通过在~/.config/swi prolog/init.pl
文件中添加指令来切换到readline
:
:- set_prolog_flag(readline, readline).
然后你会得到:
?- [user].
|: a(A,B) :- forall(A,B).
|: % user://1 compiled 0.00 sec, 1 clauses
true.
?- listing(a/2).
% autoloading user:listing/1 from /Users/pmoura/lib/swipl/library/listing
a(A, B) :-
forall(A, B).
true.
这是一个糟糕的解决方法,但它可能会对您有所帮助。请注意,
forall/2
谓词可以而且通常被定义为forall(a,B):-\+(call(a),\+call(B))
…但是在这里,我希望demo(a,B)
被扩展为forall(a,B)
。如果您不发布正在使用的术语扩展代码,很难给出建议。@PauloMoura它是编译器的一部分。这个编译器使用子句/2、
扩展子句,但是我需要在不修改定义的情况下扩展每个子句。我期望子句(demo(A,B),子句)
将子句
与forall(A,B)
统一起来,但它没有按照我的预期工作。在SWI prolog 8.1.19中,如果不将prolog\u加载到minizing模块,则会使forall(_7212,_7214)forall(_7212,_7214)正确。
清单(demo)
还显示了未扩展的代码。
?- [user].
|: a(A,B) :- forall(A,B).
|: % user://1 compiled 0.00 sec, 1 clauses
true.
?- listing(a/2).
% autoloading user:listing/1 from /Users/pmoura/lib/swipl/library/listing
a(A, B) :-
forall(A, B).
true.