[PPL-devel] [GIT] ppl/ppl(sparse_matrices): CO_Tree: optimize further lower_bound() for the DFS layout.
Marco Poletti
poletti.marco at gmail.com
Sun May 9 13:52:36 CEST 2010
Module: ppl/ppl
Branch: sparse_matrices
Commit: 4f4c3d79d1458b66d21c2cf5041c1ad7cc28ffd9
URL: http://www.cs.unipr.it/git/gitweb.cgi?p=ppl/ppl.git;a=commit;h=4f4c3d79d1458b66d21c2cf5041c1ad7cc28ffd9
Author: Marco Poletti <poletti.marco at gmail.com>
Date: Sun May 9 12:42:47 2010 +0200
CO_Tree: optimize further lower_bound() for the DFS layout.
---
src/CO_Tree.inlines.hh | 88 ++++++++++++++++++++++++++++++++++++++++++++++-
1 files changed, 86 insertions(+), 2 deletions(-)
diff --git a/src/CO_Tree.inlines.hh b/src/CO_Tree.inlines.hh
index f91f8ac..391894e 100644
--- a/src/CO_Tree.inlines.hh
+++ b/src/CO_Tree.inlines.hh
@@ -366,7 +366,49 @@ CO_Tree::lower_bound(inorder_iterator& itr, dimension_type key) {
return;
dimension_type low_index = itr.i;
- dimension_type high_index = reserved_size;
+ dimension_type high_index;
+
+ // Logarithmic search of an interval in which the key will be searched.
+ // Near (and small) intervals are tried first, to exploit the caches.
+ {
+ dimension_type hop = 1;
+ dimension_type last_low_index = low_index;
+
+ while (1) {
+
+ if (low_index > reserved_size)
+ low_index = reserved_size + 1;
+ else
+ while (indexes[low_index] == unused_index)
+ ++low_index;
+
+ PPL_ASSERT(indexes[low_index] != unused_index);
+
+ if (low_index > reserved_size) {
+ PPL_ASSERT(low_index <= reserved_size + 1);
+ high_index = low_index - 1;
+ low_index = last_low_index;
+ break;
+ }
+
+ if (indexes[low_index] == key) {
+ itr.i = low_index;
+ return;
+ }
+
+ if (indexes[low_index] > key) {
+ high_index = low_index - 1;
+ low_index = last_low_index;
+ break;
+ }
+
+ PPL_ASSERT(indexes[low_index] < key);
+
+ last_low_index = low_index;
+ low_index += hop;
+ hop *= 2;
+ }
+ }
PPL_ASSERT(low_index > 0);
@@ -461,7 +503,49 @@ CO_Tree::lower_bound(inorder_const_iterator& itr, dimension_type key) const {
return;
dimension_type low_index = itr.i;
- dimension_type high_index = reserved_size;
+ dimension_type high_index;
+
+ // Logarithmic search of an interval in which the key will be searched.
+ // Near (and small) intervals are tried first, to exploit the caches.
+ {
+ dimension_type hop = 1;
+ dimension_type last_low_index = low_index;
+
+ while (1) {
+
+ if (low_index > reserved_size)
+ low_index = reserved_size + 1;
+ else
+ while (indexes[low_index] == unused_index)
+ ++low_index;
+
+ PPL_ASSERT(indexes[low_index] != unused_index);
+
+ if (low_index > reserved_size) {
+ PPL_ASSERT(low_index <= reserved_size + 1);
+ high_index = low_index - 1;
+ low_index = last_low_index;
+ break;
+ }
+
+ if (indexes[low_index] == key) {
+ itr.i = low_index;
+ return;
+ }
+
+ if (indexes[low_index] > key) {
+ high_index = low_index - 1;
+ low_index = last_low_index;
+ break;
+ }
+
+ PPL_ASSERT(indexes[low_index] < key);
+
+ last_low_index = low_index;
+ low_index += hop;
+ hop *= 2;
+ }
+ }
PPL_ASSERT(low_index > 0);
More information about the PPL-devel
mailing list