第十四章 数据结构的扩张

来源:互联网 发布:翻译阿拉伯语的软件 编辑:程序博客网 时间:2024/04/29 14:15

14.1动态顺序统计

def 我们将中序遍历树时输出的位置称为秩。

def 每个节点增加size属性,具有如下性质的红黑树称为红黑树


有了这个属性可以在O(lgn)的时间里确定一个元素的秩(OS_RANK)和查找具有给定秩的元素(OS_SELECT)。通过循环不变式简单的验证他的正确性。为维护这个新增的性质需要对insert和delete操作做一些修改



class COLOR:    RED = "red"    BLACK = "black"class TREENODE():    def __init__(self, key, color=COLOR.BLACK, parent = None):        self.key = key        self.parent = parent        self.left = None        self.right = None        self.color = color        self.size = 0class TREE():    def __init__(self):        self.nil = TREENODE(None)        self.root = self.nildef SET_SIZE(T, x):    if x != T.nil:        leftSize = 0        rightSize = 0        if x.right != T.nil:            rightSize = x.right.size        if x.left != T.nil:            leftSize = x.left.size        x.size = leftSize + rightSizedef OS_SELECT(x, i):    r = x.left.size + 1    if i == r:        return x    elif i < r:        return OS_SELECT(x.left, i)    else:        return OS_SELECT(x.right, i - r)def OS_RANK(T, x):    r = x.left.size + 1    y = x    while y != T.root:        if y == y.parent.right:            r = r + y.parent.left.size + 1        y = y.parent    return rdef INORDER_TREE_WALK(x):    if x != None:        INORDER_TREE_WALK(x.left)        print( x.key, x.color, x.size)        INORDER_TREE_WALK(x.right)def LEFT_ROTATE(T, x):    y = x.right    x.right = y.left    if y.left != T.nil:        y.left.parent = x    y.parent = x.parent    if x.parent == T.nil:        T.root = y    elif x == x.parent.left:        x.parent.left = y    else:        x.parent.right = y    y.left = x    x.parent = y        SET_SIZE(T, x)    SET_SIZE(T, y)def RIGHT_ROTATE(T, x):    y = x.left    x.left = y.right    if y.right != T.nil:        y.right.parent = x    y.parent = x.parent    if x.parent == T.nil:        T.root = y    elif x == x.parent.left:        x.parent.left = y    else:        x.parent.right = y    y.right = x    x.parent = y        SET_SIZE(T, x)    SET_SIZE(T, y)def RB_INSERT_FIXUP(T, z):    while z.parent.color == COLOR.RED:        if z.parent == z.parent.parent.left:            y = z.parent.parent.right            if y.color == COLOR.RED:                z.parent.color = COLOR.BLACK                y.color = COLOR.BLACK                z.parent.parent.color = COLOR.RED                z = z.parent.parent            else:                if z == z.parent.right:                    z = z.parent                    LEFT_ROTATE(T, z)                z.parent.color = COLOR.BLACK                z.parent.parent.color = COLOR.RED                RIGHT_ROTATE(T, z.parent.parent)        else:            y = z.parent.parent.left            if y.color == COLOR.RED:                z.parent.color = COLOR.BLACK                y.color = COLOR.BLACK                z.parent.parent.color = COLOR.RED                z = z.parent.parent            else:                if z == z.parent.left:                    z = z.parent                    RIGHT_ROTATE(T, z)                z.parent.color = COLOR.BLACK                z.parent.parent.color = COLOR.RED                LEFT_ROTATE(T, z.parent.parent)    T.root.color = COLOR.BLACKdef RB_INSERT(T, z):    z.right = T.nil    z.left = T.nil    z.parent = T.nil    z.size = 1        y = T.nil    x = T.root    while x != T.nil:        y = x        x.size = x.size + 1        if z.key < x.key:            x = x.left        else:            x = x.right    z.parent = y        if y == T.nil:        T.root = z    elif z.key < y.key:        y.left = z    else:        y.right = z    z.left = T.nil    z.right = T.nil    z.color = COLOR.RED    RB_INSERT_FIXUP(T, z)def TREE_MINIMUM(T, x):    while x.left != T.nil:        x = x.left    return xdef TREE_MAXIMUM(T, x):    while x.right != T.nil:        x = x.right    return xdef RB_TRANSPLANT(T, u, v):    if u.parent == T.nil:        T.root = v    elif u == u.parent.left:        u.parent.left = v    else:        u.parent.right = v    v.parent = u.parentdef RB_DELETE_FIXUP(T, x):    while x != T.root and x.color == COLOR.BLACK:        if x == x.parent.left:            w = x.parent.right            if w.color == COLOR.RED:                w.color = COLOR.BLACK                x.parent.color = COLOR.RED                LEFT_ROTATE(T, x.parent)                w = x.parent.right                        if w.left.color == COLOR.BLACK and w.right.color == COLOR.BLACK:                w.color = COLOR.RED                x = x.parent            else:                if w.right.color == COLOR.BLACK:                    w.left.color = COLOR.BLACK                    w.color = COLOR.RED                    RIGHT_ROTATE(T, w)                    w = x.parent.right                w.color = x.parent.color                x.parent.color = COLOR.BLACK                w.right.color = COLOR.BLACK                LEFT_ROTATE(T, x.parent)                x = T.root        else:            w = x.parent.left            if w.color == COLOR.RED:                w.color = COLOR.BLACK                x.parent.color = COLOR.RED                RIGHT_ROTATE(T, x.parent)                w = x.parent.left            if w.left.color == COLOR.BLACK and w.right.color == COLOR.BLACK:                w.color = COLOR.RED                x = x.parent            else:                if w.left.color == COLOR.BLACK:                    w.right.color = COLOR.BLACK                    w.color = COLOR.RED                    LEFT_ROTATE(T, w)                    w = x.parent.left                w.color = x.parent.color                x.parent.color = COLOR.BLACK                w.left.color = COLOR.BLACK                RIGHT_ROTATE(T, x.parent)                x = T.root    x.color = COLOR.BLACK                    def RB_DELETE(T, z):    y = z    y_original_color = y.color    if z.left == T.nil:        x = z.right        RB_TRANSPLANT(T, z, z.right)    elif z.right == T.nil:        x = z.left        RB_TRANSPLANT(T, z, z.left)    else:        y = TREE_MINIMUM(T, z.right)        y_original_color = y.color        x = y.right        if y.parent == z:            x.parent = y        else:            RB_TRANSPLANT(T, y, y.right)            y.right = z.right            y.right.parent = y        RB_TRANSPLANT(T, z, y)        y.left = z.left        y.left.parent = y        y.color = z.color    t = y    while t != T.nil:        t.size = t.size - 1        t = t.parent    if y_original_color == COLOR.BLACK:        RB_DELETE_FIXUP(T, x)    

14.2如果扩展数据结构

其中4为目的,2为手段,但是这两则需要通过3进行证明。例如:



14.3区间树

区间树是红黑树扩展的一个实例





class COLOR:    RED = "red"    BLACK = "black"class INTERVAL:    def __init__(self, low, high):        self.low = low        self.high = high    def __cmp__(self, other):        return self.low == other.low and self.high == other.high    def __lt__(self, other):        if self.low == other.low:            return self.high < other.high        return self.low < other.lowclass TREENODE():    def __init__(self, key, color=COLOR.BLACK, parent = None):        self.key = key        self.parent = parent        self.left = None        self.right = None        self.color = color        self.max = key.highclass TREE():    def __init__(self):        self.nil = TREENODE(INTERVAL(0,0))        self.root = self.nildef SET_MAX(x):    x.max = max(x.key.high, x.left.max, x.right.max)        def INTERVAL_SEARCH(T, i):    x = T.root    while x != T.nil and (x.key.low > i.high or x.key.high < i.low):        if x.left != T.nil and x.left.max >= i.low:            x = x.left        else:            x = x.right    return xdef INORDER_TREE_WALK(x):    if x != None:        INORDER_TREE_WALK(x.left)        print( x.key.low, x.key.high, x.color)        INORDER_TREE_WALK(x.right)def LEFT_ROTATE(T, x):    y = x.right    x.right = y.left    if y.left != T.nil:        y.left.parent = x    y.parent = x.parent    if x.parent == T.nil:        T.root = y    elif x == x.parent.left:        x.parent.left = y    else:        x.parent.right = y    y.left = x    x.parent = y    SET_MAX(x)    SET_MAX(y)def RIGHT_ROTATE(T, x):    y = x.left    x.left = y.right    if y.right != T.nil:        y.right.parent = x    y.parent = x.parent    if x.parent == T.nil:        T.root = y    elif x == x.parent.left:        x.parent.left = y    else:        x.parent.right = y    y.right = x    x.parent = y    SET_MAX(x)    SET_MAX(y)def RB_INSERT_FIXUP(T, z):    while z.parent.color == COLOR.RED:        if z.parent == z.parent.parent.left:            y = z.parent.parent.right            if y.color == COLOR.RED:                z.parent.color = COLOR.BLACK                y.color = COLOR.BLACK                z.parent.parent.color = COLOR.RED                z = z.parent.parent            else:                if z == z.parent.right:                    z = z.parent                    LEFT_ROTATE(T, z)                z.parent.color = COLOR.BLACK                z.parent.parent.color = COLOR.RED                RIGHT_ROTATE(T, z.parent.parent)        else:            y = z.parent.parent.left            if y.color == COLOR.RED:                z.parent.color = COLOR.BLACK                y.color = COLOR.BLACK                z.parent.parent.color = COLOR.RED                z = z.parent.parent            else:                if z == z.parent.left:                    z = z.parent                    RIGHT_ROTATE(T, z)                z.parent.color = COLOR.BLACK                z.parent.parent.color = COLOR.RED                LEFT_ROTATE(T, z.parent.parent)    T.root.color = COLOR.BLACKdef RB_INSERT(T, z):    z.right = T.nil    z.left = T.nil    z.parent = T.nil        y = T.nil    x = T.root    while x != T.nil:        y = x        x.max = max(x.max, z.max)        if z.key < x.key:            x = x.left        else:            x = x.right    z.parent = y        if y == T.nil:        T.root = z    elif z.key < y.key:        y.left = z    else:        y.right = z    z.left = T.nil    z.right = T.nil    z.color = COLOR.RED    RB_INSERT_FIXUP(T, z)def TREE_MINIMUM(T, x):    while x.left != T.nil:        x = x.left    return xdef TREE_MAXIMUM(T, x):    while x.right != T.nil:        x = x.right    return xdef RB_TRANSPLANT(T, u, v):    if u.parent == T.nil:        T.root = v    elif u == u.parent.left:        u.parent.left = v    else:        u.parent.right = v    v.parent = u.parentdef RB_DELETE_FIXUP(T, x):    while x != T.root and x.color == COLOR.BLACK:        if x == x.parent.left:            w = x.parent.right            if w.color == COLOR.RED:                w.color = COLOR.BLACK                x.parent.color = COLOR.RED                LEFT_ROTATE(T, x.parent)                w = x.parent.right                        if w.left.color == COLOR.BLACK and w.right.color == COLOR.BLACK:                w.color = COLOR.RED                x = x.parent            else:                if w.right.color == COLOR.BLACK:                    w.left.color = COLOR.BLACK                    w.color = COLOR.RED                    RIGHT_ROTATE(T, w)                    w = x.parent.right                w.color = x.parent.color                x.parent.color = COLOR.BLACK                w.right.color = COLOR.BLACK                LEFT_ROTATE(T, x.parent)                x = T.root        else:            w = x.parent.left            if w.color == COLOR.RED:                w.color = COLOR.BLACK                x.parent.color = COLOR.RED                RIGHT_ROTATE(T, x.parent)                w = x.parent.left            if w.left.color == COLOR.BLACK and w.right.color == COLOR.BLACK:                w.color = COLOR.RED                x = x.parent            else:                if w.left.color == COLOR.BLACK:                    w.right.color = COLOR.BLACK                    w.color = COLOR.RED                    LEFT_ROTATE(T, w)                    w = x.parent.left                w.color = x.parent.color                x.parent.color = COLOR.BLACK                w.left.color = COLOR.BLACK                RIGHT_ROTATE(T, x.parent)                x = T.root    x.color = COLOR.BLACK                    def RB_DELETE(T, z):    y = z    y_original_color = y.color    if z.left == T.nil:        x = z.right        RB_TRANSPLANT(T, z, z.right)    elif z.right == T.nil:        x = z.left        RB_TRANSPLANT(T, z, z.left)    else:        y = TREE_MINIMUM(T, z.right)        y_original_color = y.color        x = y.right        if y.parent == z:            x.parent = y        else:            RB_TRANSPLANT(T, y, y.right)            y.right = z.right            y.right.parent = y        RB_TRANSPLANT(T, z, y)        y.left = z.left        y.left.parent = y        y.color = z.color    t = y    while t != T.nil:        SET_MAX(t)        t = t.parent    if y_original_color == COLOR.BLACK:        RB_DELETE_FIXUP(T, x)    

习题解答


0 0
原创粉丝点击