Skip to content

Commit da07ec8

Browse files
committed
_condense!(): fix degen. root elimination
- recursively eliminate trivial (1-child) root children - stop at level required for reinsertion
1 parent 407e53d commit da07ec8

1 file changed

Lines changed: 19 additions & 21 deletions

File tree

src/rtree/adjust.jl

Lines changed: 19 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -6,27 +6,25 @@ function _condense!(node::Node, tree::RTree, tmpdetached::AbstractVector{<:Node}
66

77
if node === tree.root
88
# eliminate root if it has only one child.
9-
if level(node) > 1
10-
if length(node) == 1
11-
@debug "_condense!(): shrinking single-child root"
12-
tree.root = node[1]
13-
tree.root.parent = nothing
14-
release(tree, node)
15-
pop!(tree.nnodes_perlevel) # tree became 1 level shorter
16-
elseif isempty(node)
17-
@debug "_condense!(): resetting empty root"
18-
# reset the root to a node of minimal level to accomodate the children of tmpdetached (or leaf)
19-
root_level = mapreduce(level, max, tmpdetached, init=1)
20-
tree.root = acquire(tree, root_level == 1 ? Leaf : Branch, root_level)
21-
resize!(tree.nnodes_perlevel, root_level)
22-
fill!(tree.nnodes_perlevel, 0)
23-
tree.nnodes_perlevel[end] = 1
24-
else
25-
# due to data removal.
26-
tree.tight_mbrs && syncmbr!(node)
27-
end
28-
else
29-
# due to data removal.
9+
old_root = tree.root
10+
min_root_level = mapreduce(level, max, tmpdetached, init=1)
11+
while (level(node) > min_root_level) && (length(node) == 1)
12+
#@debug "_condense!(): shrinking single-child root (lv=$(level(node)))"
13+
tree.root = node[1]
14+
tree.root.parent = nothing
15+
release(tree, node)
16+
pop!(tree.nnodes_perlevel) # tree became 1 level shorter
17+
node = tree.root
18+
end
19+
if (level(node) >= min_root_level) && isempty(node)
20+
#@debug "_condense!(): resetting empty root (lv=$(level(node)))"
21+
# reset the root to a node of minimal level to accomodate the children of tmpdetached (or leaf)
22+
tree.root = acquire(tree, min_root_level == 1 ? Leaf : Branch, min_root_level)
23+
resize!(tree.nnodes_perlevel, min_root_level)
24+
fill!(tree.nnodes_perlevel, 0)
25+
tree.nnodes_perlevel[end] = 1
26+
elseif node === old_root
27+
# root didn't change, but MBR has to be updated due to data removal.
3028
tree.tight_mbrs && syncmbr!(node)
3129
end
3230
return node

0 commit comments

Comments
 (0)