是否有这样的数字序列(1-7,所有使用的数字,每次只有一次),会形成相等的AVL和splay树?
答案 0 :(得分:5)
嗯,为了科学的利益,我根据各自的维基百科文章在Python中实现了AVL和splay树。假设我没有在某处犯错,我的发现是没有{1,...,7}的排列产生相同的AVL和splay树。我猜想对于所有尺寸为k的组都是如此。至于这个的根本原因,我不知道。
如果有人想审核我的代码,请点击:
#####################
# Class definitions #
#####################
class Node:
''' A binary tree node '''
def __init__(self, n, p=None, l=None, r=None):
self.n = n
self.p = p
self.l = l
self.r = r
self.h = None
def __str__(self):
return "[%s %s %s]" % (self.n, (self.l if self.l else "-"), (self.r if self.r else "-"))
def __eq__(self, other):
if not isinstance(other, Node):
return NotImplemented
return self.n == other.n and self.l == other.l and self.r == other.r
def __ne__(self, other):
return not (self == other)
class HNode(Node):
''' A binary tree node, with height '''
def __init__(self, n, p=None, l=None, r=None):
super(HNode, self).__init__(n, p, l, r)
self.hup()
def lh(self):
''' Get height of left child '''
return self.l.h if self.l else 0
def rh(self):
''' Get height of right child '''
return self.r.h if self.r else 0
def hup(self):
''' Update node height '''
self.h = max(self.lh(), self.rh())+1
def __str__(self):
return "[%s (%d) %s %s]" % (self.n, self.h, (self.l if self.l else "-"), (self.r if self.r else "-"))
#########################
# Basic tree operations #
#########################
# v u
# / \ / \
# u c --> a v
# / \ / \
# a b b c
def rright(v):
''' Rotate right '''
u = v.l
u.r, v.l = v, u.r
if v.l:
v.l.p = v
u.p, v.p = v.p, u
return u
# u v
# / \ / \
# a v --> u c
# / \ / \
# b c a b
def rleft(u):
''' Rotate left '''
v = u.r
u.r, v.l = v.l, u
if u.r:
u.r.p = u
u.p, v.p = v, u.p
return v
######################
# AVL tree functions #
######################
def avl_lr(v):
v.l = rleft(v.l)
v.l.l.hup()
v.l.hup()
return avl_ll(v)
def avl_ll(v):
u = rright(v)
u.r.hup()
u.hup()
return u
def avl_rl(v):
v.r = rright(v.r)
v.r.r.hup()
v.r.hup()
return avl_rr(v)
def avl_rr(v):
u = rleft(v)
u.l.hup()
u.hup()
return u
def avl_insert(v, n, p=None):
if v is None:
return HNode(n, p)
if n < v.n:
v.l = avl_insert(v.l, n, v)
v.hup()
if v.lh() > v.rh() + 1:
return (avl_ll if (v.l.lh() > v.l.rh()) else avl_lr)(v)
else:
return v
else:
v.r = avl_insert(v.r, n, v)
v.hup()
if v.rh() > v.lh() + 1:
return (avl_rr if (v.r.rh() > v.r.lh()) else avl_rl)(v)
else:
return v
def build_avl_tree(s):
''' Build an AVL tree from the given sequence '''
v = None
for n in s:
v = avl_insert(v, n)
return v
########################
# Splay tree functions #
########################
two = lambda x: (x,x)
def bst_insert(p, n, g=None):
''' Insert a value into a BST, returning a pair consisting of
the root of the tree and the new node '''
if p is None:
return two(Node(n,g))
if n < p.n:
p.l, x = bst_insert(p.l, n, p)
else:
p.r, x = bst_insert(p.r, n, p)
return p, x
def splay(x):
''' Percolate x to the root of its tree '''
if x.p:
p = x.p
g = p.p
if g:
if p.n < g.n:
if x.n < p.n:
x = rright(rright(g))
else:
g.l = rleft(p)
x = rright(g)
else:
if x.n > p.n:
x = rleft(rleft(g))
else:
g.r = rright(p)
x = rleft(g)
p = x.p
if p:
if x.n < p.n:
p.l = x
else:
p.r = x
return splay(x)
else:
if x.n < p.n:
return rright(p)
else:
return rleft(p)
else:
return x
def splay_insert(p, n, g=None):
r, x = bst_insert(p, n, g)
return splay(x)
def build_splay_tree(s):
''' Build a splay tree from the given sequence '''
v = None
for n in s:
v = splay_insert(v, n)
return v
####################
# The Big Question #
####################
from itertools import permutations
def find_matches(n):
''' Generate all permutations of {1, ..., n} that produce
matching AVL and splay trees '''
for s in permutations(range(1, n+1)):
t1 = build_avl_tree(s)
t2 = build_splay_tree(s)
if t1 == t2:
yield s
def find_match(n):
''' Return a permutation of {1, ..., n} that produces matching
AVL and splay trees, or None if no such permutation exists '''
return next(find_matches(n), None)