From 7b51209b7bbd70069b58a6fd73f5d6d290bb5c38 Mon Sep 17 00:00:00 2001 From: Yoni Fogel <yoni@tokutek.com> Date: Mon, 31 Mar 2008 15:18:59 +0000 Subject: [PATCH] Addresses #606 Range trees now return ranges in sorted order git-svn-id: file:///svn/tokudb@3189 c7de825b-a66e-492c-adef-691d508d4ae1 --- src/range_tree/linear.c | 37 ++++++++++++++++++++++++++++++++++--- 1 file changed, 34 insertions(+), 3 deletions(-) diff --git a/src/range_tree/linear.c b/src/range_tree/linear.c index e7fd1095f11..134938eb707 100644 --- a/src/range_tree/linear.c +++ b/src/range_tree/linear.c @@ -90,6 +90,25 @@ static inline BOOL toku__rt_exact(toku_range_tree* tree, tree->data_cmp(a->data, b->data) == 0); } +static inline int toku__rt_cmp(toku_range_tree* tree, + toku_range* a, toku_range* b) { + int cmp = 0; + assert(tree); + assert(a); + assert(b); + + cmp = tree->end_cmp(a->ends.left, b->ends.left); + if (cmp!=0) { goto cleanup; } + cmp = tree->end_cmp(a->ends.right, b->ends.right); + if (cmp!=0) { goto cleanup; } + cmp = tree->data_cmp(a->data, b->data); + if (cmp!=0) { goto cleanup; } + + cmp = 0; +cleanup: + return cmp; +} + int toku_rt_create(toku_range_tree** ptree, int (*end_cmp)(const toku_point*,const toku_point*), int (*data_cmp)(const TXNID,const TXNID), @@ -162,6 +181,7 @@ int toku_rt_insert(toku_range_tree* tree, toku_range* range) { if (!tree || !range) return EINVAL; u_int32_t i; + u_int32_t move; int r; //EDOM cases @@ -175,9 +195,18 @@ int toku_rt_insert(toku_range_tree* tree, toku_range* range) { if (toku__rt_overlap(tree, &range->ends, &tree->i.ranges[i].ends)) return EDOM; } } + for (i = 0; i < tree->numelements; i++) { + if (toku__rt_cmp(tree, range, &tree->i.ranges[i]) > 0) { break; } + } + /* Goes in slot 'i' */ r = toku__rt_increase_capacity(tree, tree->numelements + 1); if (r != 0) return r; - tree->i.ranges[tree->numelements++] = *range; + tree->numelements++; + /* Shift to make room. */ + for (move = tree->numelements - 1; move > i; move--) { + tree->i.ranges[move] = tree->i.ranges[move - 1]; + } + tree->i.ranges[i] = *range; toku_rt_invalidate_iteration(tree); return 0; } @@ -185,6 +214,7 @@ int toku_rt_insert(toku_range_tree* tree, toku_range* range) { int toku_rt_delete(toku_range_tree* tree, toku_range* range) { if (!tree || !range) return EINVAL; u_int32_t i; + u_int32_t move; for (i = 0; i < tree->numelements && @@ -192,8 +222,9 @@ int toku_rt_delete(toku_range_tree* tree, toku_range* range) { i++) {} //EDOM case: Not Found if (i == tree->numelements) return EDOM; - if (i < tree->numelements - 1) { - tree->i.ranges[i] = tree->i.ranges[tree->numelements - 1]; + /* Shift left. */ + for (move = i; move < tree->numelements - 1; move++) { + tree->i.ranges[move] = tree->i.ranges[move + 1]; } toku__rt_decrease_capacity(tree, --tree->numelements); toku_rt_invalidate_iteration(tree);