有关程序的声明意义有些疑惑,打印在序言
编写需要的元素本身名单和 打印在每行的内部列表中的元素列表的规则列表的列表:有关程序的声明意义有些疑惑,打印在序言
例:
? - printList [[1,a],[2,b]])。
2 B
溶液了下列之一:到达基础案例
/* BASE CASE: The list is empty, so there is nothing to print */
printList([]).
printList([P|R]):- printList(P),
!,
nl,
printList(R).
printList([X|R]):- write(X),
!,
printList(R).
我有的printList规则当列表是空的,在这种情况下,没有什么可打印的。
如果我的基本情况我不是(在列表不为空),它调用第二条规则的printList([P | R]),现在我有我的第一个疑问:
元素P是一个列表,因为Prolog自动处理一个内部列表作为一个元素?
所以,如果我有类似:
[[1,],[2,B],[3,C],[4,D]]我有Prolog的自动匹配在这种方式:
P = [1,](第一列表作为头元件)
R = [[2,b],[3,C],[4,d] ](其他3个列表是尾部列表的元素)
然后程序在头元素(第一个列表)上调用谓词谓词,并且此版本的规则写入当前列表中的所有元素。
这是正确的解释吗?
现在我对这个项目的跟踪一些疑问,例如,如果我执行该语句我获得以下跟踪:
[trace] ?- printList([[1,a], [2,b]]).
Call: (6) printList([[1, a], [2, b]]) ? creep
Call: (7) printList([1, a]) ? creep
Call: (8) printList(1) ? creep
Fail: (8) printList(1) ? creep
Redo: (7) printList([1, a]) ? creep
Call: (8) write(1) ? creep
1
Exit: (8) write(1) ? creep
Call: (8) printList([a]) ? creep
Call: (9) printList(a) ? creep
Fail: (9) printList(a) ? creep
Redo: (8) printList([a]) ? creep
Call: (9) write(a) ? creep
a
Exit: (9) write(a) ? creep
Call: (9) printList([]) ? creep
Exit: (9) printList([]) ? creep
Exit: (8) printList([a]) ? creep
Exit: (7) printList([1, a]) ? creep
Call: (7) nl ? creep
Exit: (7) nl ? creep
Call: (7) printList([[2, b]]) ? creep
Call: (8) printList([2, b]) ? creep
Call: (9) printList(2) ? creep
Fail: (9) printList(2) ? creep
Redo: (8) printList([2, b]) ? creep
Call: (9) write(2) ? creep
2
Exit: (9) write(2) ? creep
Call: (9) printList([b]) ? creep
Call: (10) printList(b) ? creep
Fail: (10) printList(b) ? creep
Redo: (9) printList([b]) ? creep
Call: (10) write(b) ? creep
b
Exit: (10) write(b) ? creep
Call: (10) printList([]) ? creep
Exit: (10) printList([]) ? creep
Exit: (9) printList([b]) ? creep
Exit: (8) printList([2, b]) ? creep
Call: (8) nl ? creep
Exit: (8) nl ? creep
Call: (8) printList([]) ? creep
Exit: (8) printList([]) ? creep
Exit: (7) printList([[2, b]]) ? creep
Exit: (6) printList([[1, a], [2, b]]) ? creep
true.
这对我来说是很清楚(我觉得我以前的推理是正确的),但我不理解为何当它到达它调用就可以了的printList关系(这是一个简单的元素,而不是一个列表)内部列表中的元素,例如这里:
Call: (8) printList(1) ? creep
Fail: (8) printList(1) ? creep
日C计划审议了原始列表的第一个列表,然后将它必须打印的第一个元素,为什么叫这个简单的元素
在的printList关系是不是因为这个简单的元素可能反过来是内部列表吗?
是这样的:
[[[1.1,A1,A2],[1.2,B1,B2]],[2,b]的](其中我有一个包含2所列出的列表和第一个元素是包含2所列出所以程序检查列表如果一个元素是一个元素或内部列表
我觉得你过于思前想看看代码:?
printList([P|R]):- printList(P),
就在那里你可以看到printList/1
正与名单的头。事实上,printList/1
的所有规则都与列表和列表相匹配,这是人类可以立即看到的事实。但序言没有“通知”这一事实,所以如果你是打电话,说,
printList([1])
第一个匹配的规则是上面的一个,所以它会立即试图统一printList(1)
。这当然会失败,因为1不是一个列表,因此不符合printList/1
的任何规则。序言然后回溯并尝试下一个规则,这是启动这样的一个:
printList([X|R]):- write(X),
这显然将统一[1],其中X = 1,R = [],因此它明显地将写第一个元素,一个,然后照常进行。这里并没有涉及“内部列表”的魔术,据我所知,它根本不是Prolog中的一个概念(如果在编译器中处理这样的事情,它对Prolog的用户来说是隐藏的)。
序言不是通灵;它必须尝试规则来判断它们是否失败,即使这种尝试实质上是Horn子句头部的模式匹配失败。
我无法区分你的第一个问题和你的第二个问题,所以我希望这两个答案都可以。 :)
Tnx这么多;-) – AndreaNobili 2013-04-22 14:11:09