我想在 SICStus Prolog 中看到谓词目标内的执行时间。
示例:
pred :-
goal1,
time,
goal2,
time.
go :-
call(pred).
time_go :-
go,
times(go).
预期结果:
?- time_go.
times_go = 1000ms ,
times_go_goal1 = 500ms,
times_go_goal2 = 500ms
怎么做?
我在time_out(:Goal, +Time, -Result)
尝试了library(timeout)
,但我收到了这个错误:
| ?- time_out(char_code(a,N), T, Res).
! Instantiation error in argument 2 of user:time_out/3
! goal: time_out(user:char_code(a,_193),_179,_181)
| ?- time_out(char_code(a,N), 1000, Res).
N = 97,
Res = success ? ; % Res=timeout in other example
答案 0 :(得分:7)
您可以使用statistics/2
:
statistics(runtime,[Start|_]),
do_something,
statistics(runtime,[Stop|_]),
Runtime is Stop - Start.
或者,如果要包含垃圾回收时间,可以使用total_runtime
而不是runtime
。我记不起用于Start
和Stop
的单位,但它是非常粗糙的IIRC。在一个项目中,我们使用调用自定义外部C库来检索更精细的分辨率。
对time_out/3
的评论:它用于限制目标的运行时间,而不是衡量其运行时间。如果目标及时完成,则结果为success
,如果需要更多时间执行中止(在内部抛出超时异常),结果为timeout
。
答案 1 :(得分:4)
我想添加两个想法:
Prolog允许回溯,因此目标可能不止一次成功。
"运行时"你有兴趣吗?
使用statistics/2
,但不要直接执行此操作。
相反,使用类似的抽象
call_time/2
示例查询:
?- call_time((permutation([a,b,c,d,e,f,g,h,i],Xs),Xs=[_,_,g,f,e,d,c,b,a]), T_ms). Xs = [h, i, g, f, e, d, c, b, a], T_ms = 304 ; Xs = [i, h, g, f, e, d, c, b, a], T_ms = 345 ; false.
请注意call_time/2
成功完成两次,T_ms
衡量总运行时到目前为止。
答案 2 :(得分:0)
由于没有人提及它,因此如果您只想显示时间,则time / 1谓词也很有用。它已经得到了两个Prolog系统的支持,例如SWI-Prolog,Jekejeke Prolog,O-Prolog等...
Welcome to SWI-Prolog (threaded, 64 bits, version 7.7.19)
?- time((between(1,10000000,_), fail; true)).
% 10,000,001 inferences, 0.453 CPU in 0.468 seconds (97% CPU, 22068968 Lips)
true.
不幸的是,诸如GNU Prolog,SICStus Prolog之类的Prolog系统不支持它。但它与Unix time命令类似,因为它是一个带目标参数的元谓词。比石器时代更好。