Skip to content

Commit

Permalink
Merge branch 'perf/prefix-to-range'
Browse files Browse the repository at this point in the history
  • Loading branch information
marvin-j97 committed Jun 26, 2024
2 parents 8d8f87d + 7a6f888 commit 6718a59
Show file tree
Hide file tree
Showing 7 changed files with 101 additions and 182 deletions.
2 changes: 1 addition & 1 deletion Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
name = "lsm-tree"
description = "A K.I.S.S. implementation of log-structured merge trees (LSM-trees/LSMTs)"
license = "MIT OR Apache-2.0"
version = "1.1.2"
version = "1.2.0"
edition = "2021"
rust-version = "1.74.0"
readme = "README.md"
Expand Down
4 changes: 2 additions & 2 deletions src/range.rs
Original file line number Diff line number Diff line change
Expand Up @@ -69,7 +69,7 @@ impl<'a> TreeIter<'a> {

for segment in &level.segments {
if segment.metadata.key_range.contains_prefix(&prefix) {
let reader = segment.prefix(prefix.clone());
let reader = segment.prefix(&prefix);
readers.push_back(Box::new(reader));
}
}
Expand All @@ -91,7 +91,7 @@ impl<'a> TreeIter<'a> {
} else {
for segment in &level.segments {
if segment.metadata.key_range.contains_prefix(&prefix) {
let reader = segment.prefix(prefix.clone());
let reader = segment.prefix(&prefix);

if let Some(seqno) = seqno {
#[allow(clippy::option_if_let_else)]
Expand Down
14 changes: 0 additions & 14 deletions src/segment/block_index/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -81,20 +81,6 @@ pub struct BlockIndex {
}

impl BlockIndex {
// Gets the next first block handle of an index block that is untouched by the given prefix
pub fn get_prefix_upper_bound(
&self,
key: &[u8],
cache_policy: CachePolicy,
) -> crate::Result<Option<KeyedBlockHandle>> {
let Some(block_handle) = self.top_level_index.get_prefix_upper_bound(key) else {
return Ok(None);
};

let index_block = self.load_index_block(block_handle, cache_policy)?;
Ok(index_block.items.first().cloned())
}

#[must_use]
pub fn get_lowest_index_block_handle_containing_key(
&self,
Expand Down
51 changes: 0 additions & 51 deletions src/segment/block_index/top_level.rs
Original file line number Diff line number Diff line change
Expand Up @@ -48,21 +48,6 @@ impl TopLevelIndex {
Ok(Self::from_boxed_slice(items))
}

/// Returns a handle to the first index block that is not covered by the given prefix anymore
pub(crate) fn get_prefix_upper_bound(&self, prefix: &[u8]) -> Option<&KeyedBlockHandle> {
let start_idx = self.data.partition_point(|x| &*x.end_key <= prefix);

for idx in start_idx.. {
let handle = self.data.get(idx)?;

if !handle.end_key.starts_with(prefix) {
return self.data.get(idx + 1);
}
}

None
}

// TODO: these methods work using a slice of KeyedBlockHandles
// IndexBlocks are also a slice of KeyedBlockHandles
// ... see where I'm getting at...?
Expand Down Expand Up @@ -318,36 +303,6 @@ mod tests {
assert!(index.get_lowest_block_not_containing_key(b"z").is_none());
}

#[test]

fn tli_get_prefix_upper_bound() {
let index = TopLevelIndex::from_boxed_slice(Box::new([
bh("a".as_bytes().into(), 0),
bh("abc".as_bytes().into(), 10),
bh("abcabc".as_bytes().into(), 20),
bh("abcabcabc".as_bytes().into(), 30),
bh("abcysw".as_bytes().into(), 40),
bh("basd".as_bytes().into(), 50),
bh("cxy".as_bytes().into(), 70),
bh("ewqeqw".as_bytes().into(), 60),
]));

let handle = index.get_prefix_upper_bound(b"a").expect("should exist");
assert_eq!(&*handle.end_key, "cxy".as_bytes());

let handle = index.get_prefix_upper_bound(b"abc").expect("should exist");
assert_eq!(&*handle.end_key, "cxy".as_bytes());

let handle = index.get_prefix_upper_bound(b"basd").expect("should exist");
assert_eq!(&*handle.end_key, "ewqeqw".as_bytes());

let result = index.get_prefix_upper_bound(b"cxy");
assert!(result.is_none());

let result = index.get_prefix_upper_bound(b"ewqeqw");
assert!(result.is_none());
}

#[test]
fn tli_spanning_multi() {
let index = TopLevelIndex::from_boxed_slice(Box::new([
Expand All @@ -360,12 +315,6 @@ mod tests {
bh("c".as_bytes().into(), 60),
]));

{
let handle = index.get_prefix_upper_bound(b"a").expect("should exist");
assert_eq!(&*handle.end_key, "b".as_bytes());
assert_eq!(handle.offset, 50);
}

{
let handle = index.get_first_block_handle();
assert_eq!(&*handle.end_key, "a".as_bytes());
Expand Down
2 changes: 1 addition & 1 deletion src/segment/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -394,7 +394,7 @@ impl Segment {
///
/// Will return `Err` if an IO error occurs.
#[must_use]
pub fn prefix<K: Into<UserKey>>(&self, prefix: K) -> PrefixedReader {
pub fn prefix(&self, prefix: &[u8]) -> PrefixedReader {
PrefixedReader::new(
self.offsets.index_block_ptr,
Arc::clone(&self.descriptor_table),
Expand Down
Loading

0 comments on commit 6718a59

Please sign in to comment.