Prolog跳过一些回溯分支
我试图生成一些卡库罗斯,生成而不是解决 我有所有的规则来生成它,但是第一个结果是毫无意义的,它们就像正方形 现在,我想跳过一些分支,例如15000,以查看在该点生成的kakuro 我尝试过使用一个辅助变量,但当它失败时,Kakuro生成器会再次启动Prolog跳过一些回溯分支,prolog,Prolog,我试图生成一些卡库罗斯,生成而不是解决 我有所有的规则来生成它,但是第一个结果是毫无意义的,它们就像正方形 现在,我想跳过一些分支,例如15000,以查看在该点生成的kakuro 我尝试过使用一个辅助变量,但当它失败时,Kakuro生成器会再次启动 您可以在知识库中保留一个类似计数器的动态谓词,每次执行主谓词时该谓词都会增加。计数器的值随断言和收回而改变,即它不是主谓词中的变量,而是全局存储的值 在主谓词中,如果您添加了计数器应高于某个跳过值的条件,那么您将强制对指定迭代次数的实际规则进行回溯
您可以在知识库中保留一个类似计数器的动态谓词,每次执行主谓词时该谓词都会增加。计数器的值随
断言
和收回
而改变,即它不是主谓词中的变量,而是全局存储的值
在主谓词中,如果您添加了计数器应高于某个跳过值的条件,那么您将强制对指定迭代次数的实际规则进行回溯
作为一个例子,考虑内置谓词<代码>置换/ 2 < /代码>,计算列表的排列(注意:使用SWI PROLO测试,其他解释器具有不同的内置谓词)。示例输出:
?- permutation([1,2,3,4,5],L).
L = [1, 2, 3, 4, 5] ;
L = [1, 2, 3, 5, 4] ;
L = [1, 2, 4, 3, 5] ;
L = [1, 2, 4, 5, 3] ;
L = [1, 2, 5, 3, 4] ;
L = [1, 2, 5, 4, 3] ;
?- get_permutations([1,2,3,4,5],L2,5).
L2 = [1, 2, 5, 4, 3] ;
L2 = [1, 3, 2, 4, 5] ;
L2 = [1, 3, 2, 5, 4]
如果要跳过查询中的前5次迭代,可以使用以下代码:
:- dynamic iteration_nr/1.
iteration_nr(0).
get_permutations(L1,L2,Skip) :-
permutation(L1,L2),
iteration_nr(N),
N2 is N+1,
retract(iteration_nr(N)),
asserta(iteration_nr(N2)),
Skip < N2. % force backtracking here if counter < Skip
请注意,此处使用的是asserta
(即开始时断言),而不是不推荐使用的普通assert
。还请注意,计数器将保留该值,因此当您在同一会话中第二次运行时,结果将不同。要重置计数器,可以使用单独的初始化谓词,例如:
init_and_get_permutations(L1,L2,Skip) :-
retractall(iteration_nr(_)),
asserta(iteration_nr(0)),
get_permutations(L1,L2,Skip).
进一步注意:
assert
和retract
的使用实际上并不被认为是“干净的”Prolog编程,因为它是过程性的,并且改变了知识库。但是,对于某些应用程序,它可能很有用。我不知道它是如何工作的,但它确实有用。我需要这个快速测试我的规则,稍后我会阅读。谢谢!注意点,你在做什么?动态删除和添加规则到您的知识库中,不是吗?好消息,未来的杰尔曼会很感激的。