是否有缓存谓词的 Prolog 实现或库?
或者你会使用assertz/1和retract/1实现一个FIFO缓存,像这样:
:- dynamic cache/1.
ccall(G) :- cache(G).
ccall(G) :-
\+ cache(G),
call(G),
( findall(G0,cache(G0),Gs), length(Gs,N), N =:= 100 -> once retract(cache(_)) ; true ),
assertz(cache(G)).
在 ECLiPSe-CLP 中,至少可以使用额外的逻辑变量替换 findall/3 行:
...
( getval(cache_size) =:= 100 -> once retract(cache(_)) ; incval(cache_size) ),
...
在我的机器上,对此 ccall/1 的 1000 次调用需要 >4.00 cpu sec,而实际目标 cpu 时间可以忽略不计(0.04 cpu sec)。所以我猜想在解释器内部实现的缓存(特别是 LRU 缓存左右)仍然会优于 assertz/1 和retract/1。
我不想为每个谓词都缓存,当然,只缓存极少数谓词。一个场景可能是这样的:p([H|T], E) :- q(H,E) ; p(T,E)
没有q/2
副作用。p/2
需要一个稳定增长的列表,但总是/经常是相同的E
。