根据Prolog中公共子树的数量,树之间的递归相似度
Posted
技术标签:
【中文标题】根据Prolog中公共子树的数量,树之间的递归相似度【英文标题】:Recursive similarity between trees according to the number of common subtrees in Prolog 【发布时间】:2013-05-05 16:29:35 【问题描述】:我正在使用 SWI Prolog 研究 Prolog,我发现这个代码 sn-p 有很多困难,它发现 2 个二叉树是否有 N 个公共子树(具有相同的根):
/* BASE CASE: T1 and T2 are two tree composed of only the root X so it is
TRUE that they have exactly one common subtree
*/
delta(tree(X,[]),tree(X,[]),1):- !.
/* RULE: T1 and T2 are DIFFERENT and are structured tree.
It is TRUE that T1 and T2 have N subtrees if it is TRUE that:
*/
delta(tree(X,RX),tree(X,RX1),N):- sons(RX,SX),
sons(RX1,SX)
subdelta(RX,RX1,N),
!.
/* Else whatever T1 and T2 it is true that they have 0 common tree
(here we are in the case that the previous delta\2 predicate are
boot failed)
*/
delta(_,_,0):- !.
subdelta([],[],1).
subdelta([T1|R1],[T2|R2], N):-
delta(T1,T2,N1),
subdelta(R1,R2, NR),
N is (1 + N1)*NR.
我认为如果第一棵树与第二棵树有 N 个公共子树,则 delta/3 谓词是正确的
他这样说树:
tree(F, LIST_OF_SUBTREES).
例如,这是一棵由根 X 和两片叶子 u 和 v 组成的树:
tree(x, [tree(u,[]), tree(v,[])])
我认为 delta/3 谓词它被拒绝为 3 种可能的情况:
1) T1 和 T2 是仅由根 X 组成的两棵树,因此它们只有一个公共子树是正确的
**2) T1 和 T2 是不同的,并且是具有更多级别的结构化树,因此 T1 和 T2 有 N 个子树,如果为 TRUE,则为 TRUE:?!?!
3) 否则,如果前面的 delta\2 谓词都失败了,那么无论 T1 和 T2 有 0 个公共树都是真的
我认为这种解释是正确的(我希望如此......)但我在理解第二条规则时遇到了一些困难:什么可能是 sons/2 谓词(在我看来,这请注意内置谓词的 SWI Prolog,我正在学习的幻灯片上没有它的实现)
什么适合你?它的逻辑是什么?
Tnx
安德烈亚
【问题讨论】:
【参考方案1】:您对这三个规则的解释在我看来是合理的。为了比较,我将它们改写为:
-
如果 T1 和 T2 具有相同的值并且为空(叶节点),
delta(T1, T2, 1)
成立。
如果 T1 和 T2 有 N 个公共子树,delta(T1, T2, N)
成立。
如果 T1 和 T2 有 0 个公共子树,delta(T1, T2, 0)
成立。
我不清楚为什么这些削减是必要的。我想它们是绿色切割,因为一对树不能同时有 1、N 和 0 个公共子树。
sons/2
很有趣。我可以想象它以几种不同的方式工作。我们确定的一件事是,如果两棵树有共同的子树,sons/2
应该生成相同的值;它必须以这种方式工作,否则sons(RX, SX), sons(RX1, SX)
将永远无法工作。 (请注意,该行缺少逗号)。
剩下的一个问题是,sons/2
是通过生成所有子树还是只生成最近的一对?在我看来,它可能只生成最近的对,因为subdelta/3
调用delta/3
,导致间接递归。如果sons/2
生成所有子树,这将导致无限递归或至少大量不必要的工作。所以我敢打赌sons/2
看起来像这样:
sons(tree(_,Children), X) :- member(X, Children).
这表明至少有一种情况,delta/3
会做一些比人们乍一看更智能的事情:T1 和 T2 是彼此的反射。 T1 和 T2 的sons/2
将左与右统一,然后将右与左统一,因此您将通过共享子树获得最大相似度,但不是精确结构。
对此我最感到惊讶的是delta/3
似乎没有计算差异,它似乎计算了相似之处。这不是人们对名称所期望的,而是从实现中得出的。很难想象如何直接计算差异——上限是多少?例如,对于文件,您可以通过说每行可以相同 (0) 或不同 (1) 来计算差异,然后将差异相加。
希望这是在正确的轨道上并有所帮助!
【讨论】:
我仍然觉得这个话题很难,但现在感谢你的帮助,我认为我有新的基础来推理这个问题!!!这对我来说并不完全清楚,但在接下来的几天里,我会对此进行推理,稍后我会提出任何其他疑问:-) 我认为你在进步,但你需要对自己多一点信心。 我最大的问题是我不能参加这门课程,因为我在工作,这是我最后一次大学考试......所以我很焦虑:-) 这实际上解释了很多。我想知道你怎么会在课堂上需要这么多帮助,但如果你一个人去做,那么你能以如此之快的速度走到这一步,真是令人印象深刻。 :) 还认为我每周在办公室工作 2 晚(从 23 到 7 点),因此每周被扔石头 3 天 ... :-/ 我必须结束大学学习,然后找到一份新工作 呵呵以上是关于根据Prolog中公共子树的数量,树之间的递归相似度的主要内容,如果未能解决你的问题,请参考以下文章