我正在学习 Prolog,但我无法按照课程学习,所以我对SWI Prolog 谓词中内置的maplist的特定用途有一些疑问。
那我来解释一下我的情况:
我有一个名为的个人谓词addavl(Tree/Height, Element, NewTree/Height)
,它将元素Element
插入到 AVL 树中(原始树的高度Tree
在哪里)并生成一个新的 AVL 树,命名为包含并具有新的高度Height
NewTree
Element
Height
现在我有一个元素列表,我会将这些元素添加到 AVL 树(一开始是无效的),所以我有以下谓词(工作正常)。
我对使用内置谓词的 SWI Prolog 有一些疑问maplist/4
,我还想知道我对所有这些谓词的一般解释是否正确,或者我是否遗漏了什么。
/* Predicate that from a given list of elements build an AVL Tree: */
buildTree(List,Tree):-
length(List, N), % N: the number of element in List
/* Create L1 as a list that have the same number of element of List
For example if List have N=4 element L1=[A,B,C,D] where A,B,C,D
are variable that are not yet set
*/
length(L1,N),
/* Se fosse: append(L1,[Tree],NewList) otterrei: NewList=[A,B,C,D|Tree]
ma essendo NewList=[_|L2] so L2=[B,C,D|Tree]
*/
append(L1,[Tree],[_|L2]),
/* Put the couple (nil,0) in the L1 head so I have that A=(nil,0) that
represents an empty AVL tree:
*/
L1=[nil/0 |_],
/* Call addavl passing as parameter the tree in the L1 head, the value
to insert in the List Head and the head of L2 as the current new Tree-
When the variable Tree is reached it represents the final AVL tree
*/
maplist(addavl, L1, List, L2).
我对整个谓词的解释如下:
第一个变量包含我要插入到 AVL 树N
中的原始元素列表的长度List
然后创建一个新列表,该列表L1
具有与原始列表相同数量的元素List
,但在这种情况下L1
包含尚未设置值的变量。
因此,例如,如果原始元素列表是:
列表List = [5, 8, 3, 4]
将L1
类似于:L1 = [A, B, C, D]
哪些A, B, C, D
是尚未估值的变量。
现在有一个必须满足的陈述:
append(L1,[Tree],[_|L2]),
我是这样读的:
如果我有append(L1,[Tree],NewList)
之前的声明,我会这样:
NewList = [A,B,C,D,Tree]
ListA,B,C,D
的前一个未设置变量在哪里,并且是一个新的未设置变量。L1
Tree
但就我而言,我就是NewList = [_|L2]
这样L2 = [B,C,D,Tree]
。
现在前面append
操作的意思是创建L2
一开始就包含n
未赋值变量的列表(在前面的示例中为 4 个未赋值变量:B,C,D
, Tree
)。
这些变量中的每一个都代表一棵树,它在原始列表中插入了一个新元素List
因此,在开始时,程序通过以下指令将 void AVL 树放在此列表的头部(在我的示例中为A
变量)L1=[nil/0 |_]
:
所以在L1
变量的头部有一个高度为 0 的空树(空树是正确的 AVL 树)
现在我有了第一个疑问:通过前面的操作,我已经对列表的 head 变量进行了 valorized,L1
但是在此操作的前面,我NewList=[_|L2]
使用以下语句创建了列表:
append(L1,[Tree],[_|L2])
这意味着列表的_
匿名变量与AVL树[_|L2]
匹配?如果我在创建列表附加列表之后对头部进行了nil/0
valorized,那么这种方式也可以工作?L1
[_|L2]
L1
[Tree]
好的,如果我的解释是正确的,请继续我的第二个疑问,它与maplist SWI Prolog 内置谓词的工作方式有关..
我有:
maplist(addavl, L1, List, L2).
这个谓词到底是做什么的?
阅读官方文档:http ://www.swi-prolog.org/pldoc/man?predicate=maplist%2F2
在我看来,它的工作方式如下:
我的addavl
谓词是必须在列表的每个元素上满足的 GOAL
记住addval
谓词以这种方式起作用: addavl(Tree/Height, Element, NewTree/Height)
.
所以:
1)L1
是AVL Tree的列表(第一个是void AVL Tree nil/0
:)
2)List
是包含要插入的元素的原始列表
3)L2
是包含我将创建的 AVL 树的列表。
所以我认为现在可以通过以下方式工作:
nil/0
首先从 的头部取出 void AVL Tree ( ) L1
,从 List 取出第一个元素 do add,执行 GOAL(将此元素插入到 void AVL Tree 中)并将结果放入L2
列表头部(即,根据我之前的示例是B
变量,因此B
变量包含包含元素的第一个元素的 AVL 树List
)列表**
然后重复此过程,将所有其他元素插入到元素列表中List
,最后,列表的最后一个元素L2
(Tree
变量)将代表最终的 AVL 树,所有元素都插入其中。
我的推理是正确的还是我遗漏了什么?