refactor(tree): simplify NodeRef type by removing redundant parameters

- Removed the `Type` parameter from `NodeRef` and related structs and methods
This commit is contained in:
Janis 2025-08-15 23:25:05 +02:00
parent b11805aacd
commit 9663e95210

View file

@ -13,13 +13,7 @@
// tree.find('i') -> None // tree.find('i') -> None
use alloc::boxed::Box; use alloc::boxed::Box;
use core::{ use core::{marker::PhantomData, mem::MaybeUninit, ptr::NonNull};
borrow::Borrow,
cmp::Ordering,
marker::PhantomData,
mem::{ManuallyDrop, MaybeUninit},
ptr::NonNull,
};
mod marker { mod marker {
use core::marker::PhantomData; use core::marker::PhantomData;
@ -80,9 +74,9 @@ struct LeafNode<K, V> {
type BoxedNode<K, V> = NonNull<LeafNode<K, V>>; type BoxedNode<K, V> = NonNull<LeafNode<K, V>>;
#[derive(Debug)] #[derive(Debug)]
struct NodeRef<BorrowType, K, V, Type> { struct NodeRef<BorrowType, K, V> {
node: NonNull<LeafNode<K, V>>, node: NonNull<LeafNode<K, V>>,
_marker: PhantomData<(BorrowType, Type)>, _marker: PhantomData<BorrowType>,
} }
#[derive(Debug)] #[derive(Debug)]
@ -92,23 +86,23 @@ struct Handle<Node, Type> {
_marker: PhantomData<Type>, _marker: PhantomData<Type>,
} }
impl<'a, K: 'a, V: 'a, Type> Copy for NodeRef<marker::Immut<'a>, K, V, Type> {} impl<'a, K: 'a, V: 'a> Copy for NodeRef<marker::Immut<'a>, K, V> {}
impl<'a, K: 'a, V: 'a, Type> Clone for NodeRef<marker::Immut<'a>, K, V, Type> { impl<'a, K: 'a, V: 'a> Clone for NodeRef<marker::Immut<'a>, K, V> {
fn clone(&self) -> Self { fn clone(&self) -> Self {
*self *self
} }
} }
unsafe impl<BorrowType, K: Sync, V: Sync, Type> Sync for NodeRef<BorrowType, K, V, Type> {} unsafe impl<BorrowType, K: Sync, V: Sync> Sync for NodeRef<BorrowType, K, V> {}
unsafe impl<K: Sync, V: Sync, Type> Send for NodeRef<marker::Immut<'_>, K, V, Type> {} unsafe impl<K: Sync, V: Sync> Send for NodeRef<marker::Immut<'_>, K, V> {}
unsafe impl<K: Send, V: Send, Type> Send for NodeRef<marker::Mut<'_>, K, V, Type> {} unsafe impl<K: Send, V: Send> Send for NodeRef<marker::Mut<'_>, K, V> {}
unsafe impl<K: Send, V: Send, Type> Send for NodeRef<marker::ValMut<'_>, K, V, Type> {} unsafe impl<K: Send, V: Send> Send for NodeRef<marker::ValMut<'_>, K, V> {}
unsafe impl<K: Send, V: Send, Type> Send for NodeRef<marker::Owned, K, V, Type> {} unsafe impl<K: Send, V: Send> Send for NodeRef<marker::Owned, K, V> {}
unsafe impl<K: Send, V: Send, Type> Send for NodeRef<marker::Dying, K, V, Type> {} unsafe impl<K: Send, V: Send> Send for NodeRef<marker::Dying, K, V> {}
impl<BorrowType, K, V, Type> Handle<NodeRef<K, V, BorrowType, Type>, marker::Edge> { impl<BorrowType, K, V> Handle<NodeRef<K, V, BorrowType>, marker::Edge> {
unsafe fn new_edge(node: NodeRef<K, V, BorrowType, Type>, idx: usize) -> Self { unsafe fn new_edge(node: NodeRef<K, V, BorrowType>, idx: usize) -> Self {
Self { Self {
node, node,
idx, idx,
@ -116,8 +110,8 @@ impl<BorrowType, K, V, Type> Handle<NodeRef<K, V, BorrowType, Type>, marker::Edg
} }
} }
} }
impl<BorrowType, K, V, Type> Handle<NodeRef<K, V, BorrowType, Type>, marker::Value> { impl<BorrowType, K, V> Handle<NodeRef<K, V, BorrowType>, marker::Value> {
unsafe fn new_value(node: NodeRef<K, V, BorrowType, Type>) -> Self { unsafe fn new_value(node: NodeRef<K, V, BorrowType>) -> Self {
Self { Self {
node, node,
idx: 0, idx: 0,
@ -149,8 +143,8 @@ impl<K, V> LeafNode<K, V> {
} }
} }
impl<K, V> NodeRef<marker::Owned, K, V, marker::Leaf> { impl<K, V> NodeRef<marker::Owned, K, V> {
fn new_leaf() -> Self { fn new() -> Self {
let node = LeafNode::new(); let node = LeafNode::new();
NodeRef { NodeRef {
node: Box::into_non_null(node), node: Box::into_non_null(node),
@ -159,21 +153,7 @@ impl<K, V> NodeRef<marker::Owned, K, V, marker::Leaf> {
} }
} }
impl<BorrowType, K, V> NodeRef<BorrowType, K, V, marker::Internal> { impl<BorrowType: marker::BorrowType, K, V> NodeRef<BorrowType, K, V> {
/// Unpack a node reference that was packed as `NodeRef::parent`.
fn new_internal(node: BoxedNode<K, V>) -> Self {
let node = NodeRef {
node,
_marker: PhantomData,
};
// debug_assert!(!node.is_leaf());
node
}
}
impl<BorrowType: marker::BorrowType, K, V, Type> NodeRef<BorrowType, K, V, Type> {
/// Finds the parent of the current node. Returns `Ok(handle)` if the current /// Finds the parent of the current node. Returns `Ok(handle)` if the current
/// node actually has a parent, where `handle` points to the edge of the parent /// node actually has a parent, where `handle` points to the edge of the parent
/// that points to the current node. Returns `Err(self)` if the current node has /// that points to the current node. Returns `Err(self)` if the current node has
@ -183,9 +163,7 @@ impl<BorrowType: marker::BorrowType, K, V, Type> NodeRef<BorrowType, K, V, Type>
/// ///
/// `edge.descend().ascend().unwrap()` and `node.ascend().unwrap().descend()` should /// `edge.descend().ascend().unwrap()` and `node.ascend().unwrap().descend()` should
/// both, upon success, do nothing. /// both, upon success, do nothing.
pub(super) fn ascend( pub(super) fn ascend(self) -> Result<Handle<NodeRef<BorrowType, K, V>, marker::Edge>, Self> {
self,
) -> Result<Handle<NodeRef<BorrowType, K, V, marker::Internal>, marker::Edge>, Self> {
const { const {
assert!(BorrowType::TRAVERSAL_PERMIT); assert!(BorrowType::TRAVERSAL_PERMIT);
} }
@ -206,27 +184,14 @@ impl<BorrowType: marker::BorrowType, K, V, Type> NodeRef<BorrowType, K, V, Type>
} }
} }
impl<BorrowType: marker::BorrowType, K, V> NodeRef<BorrowType, K, V, marker::Internal> { impl<BorrowType: marker::BorrowType, K, V> Handle<NodeRef<BorrowType, K, V>, marker::Edge> {
pub(super) fn first_edge(self) -> Handle<Self, marker::Edge> {
unsafe { Handle::new_edge(self, 0) }
}
pub(super) fn last_edge(self) -> Handle<Self, marker::Edge> {
let len = self.len();
unsafe { Handle::new_edge(self, len) }
}
}
impl<BorrowType: marker::BorrowType, K, V>
Handle<NodeRef<BorrowType, K, V, marker::Internal>, marker::Edge>
{
/// Finds the node pointed to by this edge. /// Finds the node pointed to by this edge.
/// ///
/// The method name assumes you picture trees with the root node on top. /// The method name assumes you picture trees with the root node on top.
/// ///
/// `edge.descend().ascend().unwrap()` and `node.ascend().unwrap().descend()` should /// `edge.descend().ascend().unwrap()` and `node.ascend().unwrap().descend()` should
/// both, upon success, do nothing. /// both, upon success, do nothing.
pub(super) fn descend(self) -> NodeRef<BorrowType, K, V, marker::LeafOrInternal> { pub(super) fn descend(self) -> NodeRef<BorrowType, K, V> {
const { const {
assert!(BorrowType::TRAVERSAL_PERMIT); assert!(BorrowType::TRAVERSAL_PERMIT);
} }
@ -249,7 +214,7 @@ impl<BorrowType: marker::BorrowType, K, V>
} }
} }
impl<'a, K, V, NodeType, HandleType> Handle<NodeRef<marker::Mut<'a>, K, V, NodeType>, HandleType> { impl<'a, K, V, HandleType> Handle<NodeRef<marker::Mut<'a>, K, V>, HandleType> {
/// Temporarily takes out another mutable handle on the same location. Beware, as /// Temporarily takes out another mutable handle on the same location. Beware, as
/// this method is very dangerous, doubly so since it might not immediately appear /// this method is very dangerous, doubly so since it might not immediately appear
/// dangerous. /// dangerous.
@ -257,7 +222,7 @@ impl<'a, K, V, NodeType, HandleType> Handle<NodeRef<marker::Mut<'a>, K, V, NodeT
/// For details, see `NodeRef::reborrow_mut`. /// For details, see `NodeRef::reborrow_mut`.
pub(super) unsafe fn reborrow_mut( pub(super) unsafe fn reborrow_mut(
&mut self, &mut self,
) -> Handle<NodeRef<marker::Mut<'_>, K, V, NodeType>, HandleType> { ) -> Handle<NodeRef<marker::Mut<'_>, K, V>, HandleType> {
// We can't use Handle::new_kv or Handle::new_edge because we don't know our type // We can't use Handle::new_kv or Handle::new_edge because we don't know our type
Handle { Handle {
node: unsafe { self.node.reborrow_mut() }, node: unsafe { self.node.reborrow_mut() },
@ -269,9 +234,7 @@ impl<'a, K, V, NodeType, HandleType> Handle<NodeRef<marker::Mut<'a>, K, V, NodeT
/// Returns a dormant copy of this handle which can be reawakened later. /// Returns a dormant copy of this handle which can be reawakened later.
/// ///
/// See `DormantMutRef` for more details. /// See `DormantMutRef` for more details.
pub(super) fn dormant( pub(super) fn dormant(&self) -> Handle<NodeRef<marker::DormantMut, K, V>, HandleType> {
&self,
) -> Handle<NodeRef<marker::DormantMut, K, V, NodeType>, HandleType> {
Handle { Handle {
node: self.node.dormant(), node: self.node.dormant(),
idx: self.idx, idx: self.idx,
@ -280,7 +243,7 @@ impl<'a, K, V, NodeType, HandleType> Handle<NodeRef<marker::Mut<'a>, K, V, NodeT
} }
} }
impl<'a, K, V, NodeType> NodeRef<marker::Mut<'a>, K, V, NodeType> { impl<'a, K, V> NodeRef<marker::Mut<'a>, K, V> {
pub(super) fn len_mut(&mut self) -> &mut u16 { pub(super) fn len_mut(&mut self) -> &mut u16 {
// SAFETY: we have exclusive access to the entire node. // SAFETY: we have exclusive access to the entire node.
unsafe { &mut (*Self::as_leaf_ptr(self)).len } unsafe { &mut (*Self::as_leaf_ptr(self)).len }
@ -291,11 +254,11 @@ impl<'a, K, V, NodeType> NodeRef<marker::Mut<'a>, K, V, NodeType> {
} }
} }
impl<K, V, Type> NodeRef<marker::Owned, K, V, Type> { impl<K, V> NodeRef<marker::Owned, K, V> {
/// Mutably borrows the owned root node. Unlike `reborrow_mut`, this is safe /// Mutably borrows the owned root node. Unlike `reborrow_mut`, this is safe
/// because the return value cannot be used to destroy the root, and there /// because the return value cannot be used to destroy the root, and there
/// cannot be other references to the tree. /// cannot be other references to the tree.
pub(super) fn borrow_mut(&mut self) -> NodeRef<marker::Mut<'_>, K, V, Type> { pub(super) fn borrow_mut(&mut self) -> NodeRef<marker::Mut<'_>, K, V> {
NodeRef { NodeRef {
node: self.node, node: self.node,
_marker: PhantomData, _marker: PhantomData,
@ -303,7 +266,7 @@ impl<K, V, Type> NodeRef<marker::Owned, K, V, Type> {
} }
/// Slightly mutably borrows the owned root node. /// Slightly mutably borrows the owned root node.
pub(super) fn borrow_valmut(&mut self) -> NodeRef<marker::ValMut<'_>, K, V, Type> { pub(super) fn borrow_valmut(&mut self) -> NodeRef<marker::ValMut<'_>, K, V> {
NodeRef { NodeRef {
node: self.node, node: self.node,
_marker: PhantomData, _marker: PhantomData,
@ -312,7 +275,7 @@ impl<K, V, Type> NodeRef<marker::Owned, K, V, Type> {
/// Irreversibly transitions to a reference that permits traversal and offers /// Irreversibly transitions to a reference that permits traversal and offers
/// destructive methods and little else. /// destructive methods and little else.
pub(super) fn into_dying(self) -> NodeRef<marker::Dying, K, V, Type> { pub(super) fn into_dying(self) -> NodeRef<marker::Dying, K, V> {
NodeRef { NodeRef {
node: self.node, node: self.node,
_marker: PhantomData, _marker: PhantomData,
@ -320,7 +283,7 @@ impl<K, V, Type> NodeRef<marker::Owned, K, V, Type> {
} }
} }
impl<'a, K, V, Type> NodeRef<marker::Mut<'a>, K, V, Type> { impl<'a, K, V> NodeRef<marker::Mut<'a>, K, V> {
/// Temporarily takes out another mutable reference to the same node. Beware, as /// Temporarily takes out another mutable reference to the same node. Beware, as
/// this method is very dangerous, doubly so since it might not immediately appear /// this method is very dangerous, doubly so since it might not immediately appear
/// dangerous. /// dangerous.
@ -331,7 +294,7 @@ impl<'a, K, V, Type> NodeRef<marker::Mut<'a>, K, V, Type> {
// FIXME(@gereeter) consider adding yet another type parameter to `NodeRef` // FIXME(@gereeter) consider adding yet another type parameter to `NodeRef`
// that restricts the use of navigation methods on reborrowed pointers, // that restricts the use of navigation methods on reborrowed pointers,
// preventing this unsafety. // preventing this unsafety.
unsafe fn reborrow_mut(&mut self) -> NodeRef<marker::Mut<'_>, K, V, Type> { unsafe fn reborrow_mut(&mut self) -> NodeRef<marker::Mut<'_>, K, V> {
NodeRef { NodeRef {
node: self.node, node: self.node,
_marker: PhantomData, _marker: PhantomData,
@ -354,7 +317,7 @@ impl<'a, K, V, Type> NodeRef<marker::Mut<'a>, K, V, Type> {
/// Returns a dormant copy of this node with its lifetime erased which can /// Returns a dormant copy of this node with its lifetime erased which can
/// be reawakened later. /// be reawakened later.
pub(super) fn dormant(&self) -> NodeRef<marker::DormantMut, K, V, Type> { pub(super) fn dormant(&self) -> NodeRef<marker::DormantMut, K, V> {
NodeRef { NodeRef {
node: self.node, node: self.node,
_marker: PhantomData, _marker: PhantomData,
@ -362,7 +325,7 @@ impl<'a, K, V, Type> NodeRef<marker::Mut<'a>, K, V, Type> {
} }
} }
impl<'a, K: 'a, V: 'a, BorrowType> NodeRef<BorrowType, K, V, marker::Internal> { impl<'a, K: 'a, V: 'a, BorrowType> NodeRef<BorrowType, K, V> {
/// Borrows shared access to an element of the key storage area. /// Borrows shared access to an element of the key storage area.
/// ///
/// # Safety /// # Safety
@ -400,7 +363,7 @@ impl<'a, K: 'a, V: 'a, BorrowType> NodeRef<BorrowType, K, V, marker::Internal> {
} }
} }
impl<'a, K: 'a, V: 'a, NodeType> NodeRef<marker::Mut<'a>, K, V, NodeType> { impl<'a, K: 'a, V: 'a> NodeRef<marker::Mut<'a>, K, V> {
/// Borrows exclusive access to an element of the key storage area. /// Borrows exclusive access to an element of the key storage area.
/// ///
/// # Safety /// # Safety
@ -438,14 +401,14 @@ impl<'a, K: 'a, V: 'a, NodeType> NodeRef<marker::Mut<'a>, K, V, NodeType> {
} }
} }
impl<K, V, Type> NodeRef<marker::DormantMut, K, V, Type> { impl<K, V> NodeRef<marker::DormantMut, K, V> {
/// Revert to the unique borrow initially captured. /// Revert to the unique borrow initially captured.
/// ///
/// # Safety /// # Safety
/// ///
/// The reborrow must have ended, i.e., the reference returned by `new` and /// The reborrow must have ended, i.e., the reference returned by `new` and
/// all pointers and references derived from it, must not be used anymore. /// all pointers and references derived from it, must not be used anymore.
pub(super) unsafe fn awaken<'a>(self) -> NodeRef<marker::Mut<'a>, K, V, Type> { pub(super) unsafe fn awaken<'a>(self) -> NodeRef<marker::Mut<'a>, K, V> {
NodeRef { NodeRef {
node: self.node, node: self.node,
_marker: PhantomData, _marker: PhantomData,
@ -453,16 +416,14 @@ impl<K, V, Type> NodeRef<marker::DormantMut, K, V, Type> {
} }
} }
impl<K, V, NodeType, HandleType> Handle<NodeRef<marker::DormantMut, K, V, NodeType>, HandleType> { impl<K, V, HandleType> Handle<NodeRef<marker::DormantMut, K, V>, HandleType> {
/// Revert to the unique borrow initially captured. /// Revert to the unique borrow initially captured.
/// ///
/// # Safety /// # Safety
/// ///
/// The reborrow must have ended, i.e., the reference returned by `new` and /// The reborrow must have ended, i.e., the reference returned by `new` and
/// all pointers and references derived from it, must not be used anymore. /// all pointers and references derived from it, must not be used anymore.
pub(super) unsafe fn awaken<'a>( pub(super) unsafe fn awaken<'a>(self) -> Handle<NodeRef<marker::Mut<'a>, K, V>, HandleType> {
self,
) -> Handle<NodeRef<marker::Mut<'a>, K, V, NodeType>, HandleType> {
Handle { Handle {
node: unsafe { self.node.awaken() }, node: unsafe { self.node.awaken() },
idx: self.idx, idx: self.idx,
@ -471,7 +432,7 @@ impl<K, V, NodeType, HandleType> Handle<NodeRef<marker::DormantMut, K, V, NodeTy
} }
} }
impl<BorrowType, K, V, NodeType> NodeRef<BorrowType, K, V, NodeType> { impl<BorrowType, K, V> NodeRef<BorrowType, K, V> {
/// Finds the length of the node. This is the number of keys or values. /// Finds the length of the node. This is the number of keys or values.
/// The number of edges is `len() + 1`. /// The number of edges is `len() + 1`.
/// Note that, despite being safe, calling this function can have the side effect /// Note that, despite being safe, calling this function can have the side effect
@ -487,13 +448,13 @@ impl<BorrowType, K, V, NodeType> NodeRef<BorrowType, K, V, NodeType> {
} }
} }
impl<BorrowType, K, V, Type> NodeRef<BorrowType, K, V, Type> { impl<BorrowType, K, V> NodeRef<BorrowType, K, V> {
pub(super) fn is_leaf(&self) -> bool { pub(super) fn is_leaf(&self) -> bool {
unsafe { (*Self::as_leaf_ptr(self)).len == 0 } unsafe { (*Self::as_leaf_ptr(self)).len == 0 }
} }
/// Temporarily takes out another, immutable reference to the same node. /// Temporarily takes out another, immutable reference to the same node.
pub(super) fn reborrow(&self) -> NodeRef<marker::Immut<'_>, K, V, Type> { pub(super) fn reborrow(&self) -> NodeRef<marker::Immut<'_>, K, V> {
NodeRef { NodeRef {
node: self.node, node: self.node,
_marker: PhantomData, _marker: PhantomData,
@ -521,7 +482,7 @@ impl<BorrowType, K, V, Type> NodeRef<BorrowType, K, V, Type> {
} }
} }
impl<'a, K: 'a, V: 'a> NodeRef<marker::Immut<'a>, K, V, marker::Internal> { impl<'a, K: 'a, V: 'a> NodeRef<marker::Immut<'a>, K, V> {
/// Borrows a view into the keys stored in the node. /// Borrows a view into the keys stored in the node.
pub(super) fn keys(&self) -> &[K] { pub(super) fn keys(&self) -> &[K] {
unsafe { self.key_area(..self.len()).assume_init_ref() } unsafe { self.key_area(..self.len()).assume_init_ref() }
@ -532,13 +493,9 @@ impl<'a, K: 'a, V: 'a> NodeRef<marker::Immut<'a>, K, V, marker::Internal> {
} }
} }
impl<BorrowType, K, V, NodeType, HandleType> impl<BorrowType, K, V, HandleType> Handle<NodeRef<BorrowType, K, V>, HandleType> {
Handle<NodeRef<BorrowType, K, V, NodeType>, HandleType>
{
/// Temporarily takes out another immutable handle on the same location. /// Temporarily takes out another immutable handle on the same location.
pub(super) fn reborrow( pub(super) fn reborrow(&self) -> Handle<NodeRef<marker::Immut<'_>, K, V>, HandleType> {
&self,
) -> Handle<NodeRef<marker::Immut<'_>, K, V, NodeType>, HandleType> {
// We can't use Handle::new_kv or Handle::new_edge because we don't know our type // We can't use Handle::new_kv or Handle::new_edge because we don't know our type
Handle { Handle {
node: self.node.reborrow(), node: self.node.reborrow(),
@ -548,7 +505,7 @@ impl<BorrowType, K, V, NodeType, HandleType>
} }
} }
impl<'a, K: 'a, V: 'a, Type> NodeRef<marker::Immut<'a>, K, V, Type> { impl<'a, K: 'a, V: 'a> NodeRef<marker::Immut<'a>, K, V> {
/// Exposes the leaf portion of any leaf or internal node in an immutable tree. /// Exposes the leaf portion of any leaf or internal node in an immutable tree.
fn into_leaf(self) -> &'a LeafNode<K, V> { fn into_leaf(self) -> &'a LeafNode<K, V> {
let ptr = Self::as_leaf_ptr(&self); let ptr = Self::as_leaf_ptr(&self);
@ -557,7 +514,7 @@ impl<'a, K: 'a, V: 'a, Type> NodeRef<marker::Immut<'a>, K, V, Type> {
} }
} }
impl<'a, K: 'a, V: 'a, NodeType> Handle<NodeRef<marker::Immut<'a>, K, V, NodeType>, marker::Value> { impl<'a, K: 'a, V: 'a> Handle<NodeRef<marker::Immut<'a>, K, V>, marker::Value> {
pub(super) unsafe fn into_value(self) -> &'a V { pub(super) unsafe fn into_value(self) -> &'a V {
let leaf = self.node.into_leaf(); let leaf = self.node.into_leaf();
let v = leaf.value.as_ref().unwrap(); let v = leaf.value.as_ref().unwrap();
@ -565,7 +522,7 @@ impl<'a, K: 'a, V: 'a, NodeType> Handle<NodeRef<marker::Immut<'a>, K, V, NodeTyp
} }
} }
impl<'a, K: 'a, V: 'a, NodeType> Handle<NodeRef<marker::Mut<'a>, K, V, NodeType>, marker::Value> { impl<'a, K: 'a, V: 'a> Handle<NodeRef<marker::Mut<'a>, K, V>, marker::Value> {
pub(super) unsafe fn value_mut(&mut self) -> &mut V { pub(super) unsafe fn value_mut(&mut self) -> &mut V {
let leaf = self.node.as_leaf_mut(); let leaf = self.node.as_leaf_mut();
let v = leaf.value.as_mut().unwrap(); let v = leaf.value.as_mut().unwrap();
@ -578,44 +535,13 @@ impl<'a, K: 'a, V: 'a, NodeType> Handle<NodeRef<marker::Mut<'a>, K, V, NodeType>
} }
} }
impl<BorrowType, K, V> Handle<NodeRef<BorrowType, K, V, marker::Leaf>, marker::Edge> { pub(super) enum ForceResult<Node> {
pub(super) fn forget_node_type( Leaf(Node),
self, Internal(Node),
) -> Handle<NodeRef<BorrowType, K, V, marker::LeafOrInternal>, marker::Edge> {
unsafe { Handle::new_edge(self.node.forget_type(), self.idx) }
}
} }
impl<BorrowType, K, V> Handle<NodeRef<BorrowType, K, V, marker::Internal>, marker::Edge> { impl<BorrowType, K, V, HandleType> Handle<NodeRef<BorrowType, K, V>, HandleType> {
pub(super) fn forget_node_type( fn force(self) -> ForceResult<Handle<NodeRef<BorrowType, K, V>, HandleType>> {
self,
) -> Handle<NodeRef<BorrowType, K, V, marker::LeafOrInternal>, marker::Edge> {
unsafe { Handle::new_edge(self.node.forget_type(), self.idx) }
}
}
impl<BorrowType, K, V> Handle<NodeRef<BorrowType, K, V, marker::Leaf>, marker::Value> {
pub(super) fn forget_node_type(
self,
) -> Handle<NodeRef<BorrowType, K, V, marker::LeafOrInternal>, marker::Value> {
unsafe { Handle::new_value(self.node.forget_type()) }
}
}
pub(super) enum ForceResult<Leaf, Internal> {
Leaf(Leaf),
Internal(Internal),
}
impl<BorrowType, K, V, NodeType, HandleType>
Handle<NodeRef<BorrowType, K, V, NodeType>, HandleType>
{
fn force(
self,
) -> ForceResult<
Handle<NodeRef<BorrowType, K, V, marker::Leaf>, HandleType>,
Handle<NodeRef<BorrowType, K, V, marker::Internal>, HandleType>,
> {
match self.node.force() { match self.node.force() {
ForceResult::Leaf(leaf) => ForceResult::Leaf(Handle { ForceResult::Leaf(leaf) => ForceResult::Leaf(Handle {
node: leaf, node: leaf,
@ -631,57 +557,17 @@ impl<BorrowType, K, V, NodeType, HandleType>
} }
} }
impl<BorrowType, K, V, NodeType> NodeRef<BorrowType, K, V, NodeType> { impl<BorrowType, K, V> NodeRef<BorrowType, K, V> {
fn force( fn force(self) -> ForceResult<NodeRef<BorrowType, K, V>> {
self,
) -> ForceResult<
NodeRef<BorrowType, K, V, marker::Leaf>,
NodeRef<BorrowType, K, V, marker::Internal>,
> {
if self.is_leaf() { if self.is_leaf() {
ForceResult::Leaf(NodeRef { ForceResult::Leaf(self)
node: self.node,
_marker: PhantomData,
})
} else { } else {
ForceResult::Internal(NodeRef { ForceResult::Internal(self)
node: self.node,
_marker: PhantomData,
})
} }
} }
} }
impl<BorrowType, K, V> NodeRef<BorrowType, K, V, marker::Leaf> { impl<'a, K, V> NodeRef<marker::Mut<'a>, K, V> {
/// Removes any static information asserting that this node is a `Leaf` node.
pub(super) fn forget_type(self) -> NodeRef<BorrowType, K, V, marker::LeafOrInternal> {
NodeRef {
node: self.node,
_marker: PhantomData,
}
}
}
impl<BorrowType, K, V> NodeRef<BorrowType, K, V, marker::Internal> {
/// Removes any static information asserting that this node is an `Internal` node.
pub(super) fn forget_type(self) -> NodeRef<BorrowType, K, V, marker::LeafOrInternal> {
NodeRef {
node: self.node,
_marker: PhantomData,
}
}
}
impl<BorrowType, K, V, Type> NodeRef<BorrowType, K, V, Type> {
pub(super) fn as_leaf_or_internal(self) -> NodeRef<BorrowType, K, V, marker::LeafOrInternal> {
NodeRef {
node: self.node,
_marker: PhantomData,
}
}
}
impl<'a, K, V, Type> NodeRef<marker::Mut<'a>, K, V, Type> {
pub(super) fn grow_node(&mut self) { pub(super) fn grow_node(&mut self) {
// grow the node // grow the node
let Some(new_capacity) = self.capacity_mut().checked_mul(2) else { let Some(new_capacity) = self.capacity_mut().checked_mul(2) else {
@ -722,12 +608,12 @@ impl<'a, K, V, Type> NodeRef<marker::Mut<'a>, K, V, Type> {
} }
} }
impl<K, V, Type> NodeRef<marker::Owned, K, V, Type> { impl<K, V> NodeRef<marker::Owned, K, V> {
pub(super) fn reparent<'a, NodeType>( pub(super) fn reparent<'a>(
mut self, mut self,
mut parent: Handle<NodeRef<marker::Mut<'a>, K, V, NodeType>, marker::Edge>, mut parent: Handle<NodeRef<marker::Mut<'a>, K, V>, marker::Edge>,
key: K, key: K,
) -> NodeRef<marker::Mut<'a>, K, V, Type> ) -> NodeRef<marker::Mut<'a>, K, V>
where where
K: 'a, K: 'a,
V: 'a, V: 'a,
@ -759,42 +645,21 @@ impl<K, V, Type> NodeRef<marker::Owned, K, V, Type> {
} }
} }
impl<BorrowType, K, V> Handle<NodeRef<BorrowType, K, V, marker::LeafOrInternal>, marker::Edge> { impl<BorrowType, K, V> Handle<NodeRef<BorrowType, K, V>, marker::Edge> {
/// Converts this edge handle into a value handle. /// Converts this edge handle into a value handle.
pub(super) fn into_value( /// IMPORTANT: this handle points to the value of the node, not the edge.
self, pub(super) fn into_value(self) -> Handle<NodeRef<BorrowType, K, V>, marker::Value> {
) -> Handle<NodeRef<BorrowType, K, V, marker::LeafOrInternal>, marker::Value> {
unsafe { Handle::new_value(self.node) } unsafe { Handle::new_value(self.node) }
} }
} }
impl<'a, K, V> NodeRef<marker::Mut<'a>, K, V, marker::LeafOrInternal> { impl<'a, K: 'a, V: 'a> Handle<NodeRef<marker::Mut<'a>, K, V>, marker::Edge> {
/// Unsafely asserts to the compiler the static information that this node is a `Leaf`.
pub(super) unsafe fn cast_to_leaf_unchecked(
self,
) -> NodeRef<marker::Mut<'a>, K, V, marker::Leaf> {
NodeRef {
node: self.node,
_marker: PhantomData,
}
}
/// Unsafely asserts to the compiler the static information that this node is an `Internal`.
unsafe fn cast_to_internal_unchecked(self) -> NodeRef<marker::Mut<'a>, K, V, marker::Internal> {
NodeRef {
node: self.node,
_marker: PhantomData,
}
}
}
impl<'a, K: 'a, V: 'a, Type> Handle<NodeRef<marker::Mut<'a>, K, V, Type>, marker::Edge> {
/// Inserts a key-value pair into /// Inserts a key-value pair into
pub(super) unsafe fn insert_recursing<Q>( pub(super) unsafe fn insert_recursing<Q>(
mut self, mut self,
mut key_seq: Q, mut key_seq: Q,
val: V, val: V,
) -> Handle<NodeRef<marker::Mut<'a>, K, V, marker::LeafOrInternal>, marker::Value> ) -> Handle<NodeRef<marker::Mut<'a>, K, V>, marker::Value>
where where
Q: Iterator<Item = K>, Q: Iterator<Item = K>,
K: Ord, K: Ord,
@ -803,11 +668,11 @@ impl<'a, K: 'a, V: 'a, Type> Handle<NodeRef<marker::Mut<'a>, K, V, Type>, marker
// key has run out: insert value here. // key has run out: insert value here.
self.node.as_leaf_mut().value = Some(val); self.node.as_leaf_mut().value = Some(val);
// TODO: handle occupied values. // TODO: handle occupied values.
return unsafe { Handle::new_value(self.node.as_leaf_or_internal()) }; return unsafe { Handle::new_value(self.node) };
}; };
let last = unsafe { let last = unsafe {
let child = NodeRef::new_leaf().reparent(self, key); let child = NodeRef::new().reparent(self, key);
Handle::new_edge(child, 0) Handle::new_edge(child, 0)
.insert_recursing(key_seq, val) .insert_recursing(key_seq, val)
@ -825,16 +690,13 @@ mod search {
use core::borrow::Borrow; use core::borrow::Borrow;
use core::cmp::Ordering; use core::cmp::Ordering;
pub(super) enum SearchResult<BorrowType, K, V, FoundType, GoDownType> { pub(super) enum SearchResult<BorrowType, K, V> {
/// The node which contains the value for the key. /// The node which contains the value for the key.
Found(Handle<NodeRef<BorrowType, K, V, FoundType>, marker::Value>), Found(Handle<NodeRef<BorrowType, K, V>, marker::Value>),
/// The key was found, and the search should continue at the given edge. /// The key was found, and the search should continue at the given edge.
GoDown(Handle<NodeRef<BorrowType, K, V, GoDownType>, marker::Edge>), GoDown(Handle<NodeRef<BorrowType, K, V>, marker::Edge>),
/// The key was not found, and should be inserted at the given position. /// The key was not found, and should be inserted at the given position.
Insert( Insert(K, Handle<NodeRef<BorrowType, K, V>, marker::Edge>),
K,
Handle<NodeRef<BorrowType, K, V, FoundType>, marker::Edge>,
),
} }
pub(super) enum IndexResult { pub(super) enum IndexResult {
@ -842,11 +704,8 @@ mod search {
Insert(usize), Insert(usize),
} }
impl<BorrowType: marker::BorrowType, K, V> NodeRef<BorrowType, K, V, marker::LeafOrInternal> { impl<BorrowType: marker::BorrowType, K, V> NodeRef<BorrowType, K, V> {
pub(super) fn search_tree<Q>( pub(super) fn search_tree<Q>(mut self, mut key: Q) -> SearchResult<BorrowType, K, V>
mut self,
mut key: Q,
) -> SearchResult<BorrowType, K, V, marker::LeafOrInternal, marker::Leaf>
where where
Q: Iterator<Item = K>, Q: Iterator<Item = K>,
K: Ord, K: Ord,
@ -864,11 +723,8 @@ mod search {
} }
} }
impl<BorrowType, K, V, Type> NodeRef<BorrowType, K, V, Type> { impl<BorrowType, K, V> NodeRef<BorrowType, K, V> {
fn search_node<Q>( fn search_node<Q>(self, mut key: Q) -> SearchResult<BorrowType, K, V>
self,
mut key: Q,
) -> SearchResult<BorrowType, K, V, marker::LeafOrInternal, marker::Internal>
where where
Q: Iterator<Item = K>, Q: Iterator<Item = K>,
K: Ord, K: Ord,
@ -878,23 +734,21 @@ mod search {
let Some(key) = key.next() else { let Some(key) = key.next() else {
// key has run out, a value is either occupying this // key has run out, a value is either occupying this
// node, or belongs here. // node, or belongs here.
return SearchResult::Found(unsafe { return SearchResult::Found(unsafe { Handle::new_value(self) });
Handle::new_value(self.as_leaf_or_internal())
});
}; };
match self.force() { match self.force() {
// self is a leaf node and doesn't contain any keys: // self is a leaf node and doesn't contain any keys:
// a new leaf node should be inserted at this point. // a new leaf node should be inserted at this point.
ForceResult::Leaf(leaf) => { ForceResult::Leaf(leaf) => {
SearchResult::Insert(key, unsafe { Handle::new_edge(leaf.forget_type(), 0) }) SearchResult::Insert(key, unsafe { Handle::new_edge(leaf, 0) })
} }
ForceResult::Internal(internal) => { ForceResult::Internal(internal) => {
// search through the keys of the internal node // search through the keys of the internal node
match unsafe { internal.find_key_index(&key, 0) } { match unsafe { internal.find_key_index(&key, 0) } {
IndexResult::Insert(idx) => Insert(key, unsafe { IndexResult::Insert(idx) => Insert(key, unsafe {
// the key wasn't present, but should be inserted at `idx`. // the key wasn't present, but should be inserted at `idx`.
Handle::new_edge(internal.forget_type(), idx) Handle::new_edge(internal, idx)
}), }),
IndexResult::Edge(idx) => { IndexResult::Edge(idx) => {
// the key was found, continue searching down the edge // the key was found, continue searching down the edge
@ -906,7 +760,7 @@ mod search {
} }
} }
impl<BorrowType, K, V> NodeRef<BorrowType, K, V, marker::Internal> { impl<BorrowType, K, V> NodeRef<BorrowType, K, V> {
/// # Safety /// # Safety
/// `start_index` must be a valid edge index for the node. /// `start_index` must be a valid edge index for the node.
unsafe fn find_key_index<Q: ?Sized>(&self, key: &Q, start_index: usize) -> IndexResult unsafe fn find_key_index<Q: ?Sized>(&self, key: &Q, start_index: usize) -> IndexResult
@ -975,8 +829,8 @@ mod search {
} }
} }
enum HandleOrTree<'a, BorrowType, K, V, NodeType, HandleType> { enum HandleOrTree<'a, BorrowType, K, V, HandleType> {
Handle(Handle<NodeRef<BorrowType, K, V, NodeType>, HandleType>), Handle(Handle<NodeRef<BorrowType, K, V>, HandleType>),
Tree(borrow::DormantMutRef<'a, Tree<K, V>>), Tree(borrow::DormantMutRef<'a, Tree<K, V>>),
} }
@ -1035,14 +889,12 @@ mod entry {
Q: Iterator<Item = K>, Q: Iterator<Item = K>,
{ {
pub(super) key: Q, pub(super) key: Q,
pub(super) handle: pub(super) handle: super::HandleOrTree<'a, marker::Mut<'a>, K, V, marker::Edge>,
super::HandleOrTree<'a, marker::Mut<'a>, K, V, marker::LeafOrInternal, marker::Edge>,
pub(super) _marker: PhantomData<&'a mut (K, V)>, pub(super) _marker: PhantomData<&'a mut (K, V)>,
} }
pub struct OccupiedEntry<'a, K, V> { pub struct OccupiedEntry<'a, K, V> {
pub(super) handle: pub(super) handle: Handle<NodeRef<marker::Mut<'a>, K, V>, marker::Value>,
Handle<NodeRef<marker::Mut<'a>, K, V, marker::LeafOrInternal>, marker::Value>,
pub(super) _marker: PhantomData<&'a mut (K, V)>, pub(super) _marker: PhantomData<&'a mut (K, V)>,
} }
@ -1056,7 +908,7 @@ mod entry {
pub fn into_subtree(self) -> super::subtree::Subtree<K, V, marker::Mut<'a>> { pub fn into_subtree(self) -> super::subtree::Subtree<K, V, marker::Mut<'a>> {
super::subtree::Subtree { super::subtree::Subtree {
root: self.handle.node.as_leaf_or_internal(), root: self.handle.node,
} }
} }
} }
@ -1084,11 +936,7 @@ mod entry {
HandleOrTree::Tree(mut tree) => { HandleOrTree::Tree(mut tree) => {
// SAFETY: there are no nodes in the tree yet // SAFETY: there are no nodes in the tree yet
let tree = unsafe { tree.reborrow() }; let tree = unsafe { tree.reborrow() };
let root = let root = tree.root.insert(NodeRef::new());
tree.root
.insert(NodeRef::new_internal(alloc::boxed::Box::into_non_null(
LeafNode::new(),
)));
unsafe { unsafe {
Handle::new_edge(root.borrow_mut(), 0).insert_recursing(self.key, value) Handle::new_edge(root.borrow_mut(), 0).insert_recursing(self.key, value)
@ -1118,7 +966,7 @@ mod subtree {
// BorrowType may be one of `Immut`, `Mut`. // BorrowType may be one of `Immut`, `Mut`.
pub struct Subtree<K, V, BorrowType> { pub struct Subtree<K, V, BorrowType> {
pub(super) root: NodeRef<BorrowType, K, V, marker::LeafOrInternal>, pub(super) root: NodeRef<BorrowType, K, V>,
} }
impl<K, V, BorrowType> Subtree<K, V, BorrowType> impl<K, V, BorrowType> Subtree<K, V, BorrowType>
@ -1145,9 +993,7 @@ mod subtree {
{ {
let root = self.root.reborrow(); let root = self.root.reborrow();
match root.search_tree(&mut key_seq) { match root.search_tree(&mut key_seq) {
search::SearchResult::Found(handle) => Some(Subtree { search::SearchResult::Found(handle) => Some(Subtree { root: handle.node }),
root: handle.node.as_leaf_or_internal(),
}),
_ => { _ => {
// key not found // key not found
None None
@ -1183,9 +1029,7 @@ mod subtree {
{ {
let root = unsafe { self.root.reborrow_mut() }; let root = unsafe { self.root.reborrow_mut() };
match root.search_tree(&mut key_seq) { match root.search_tree(&mut key_seq) {
search::SearchResult::Found(handle) => Some(Subtree { search::SearchResult::Found(handle) => Some(Subtree { root: handle.node }),
root: handle.node.as_leaf_or_internal(),
}),
_ => { _ => {
// key not found // key not found
None None
@ -1209,7 +1053,7 @@ mod subtree {
}), }),
search::SearchResult::GoDown(handle) => Vacant(VacantEntry { search::SearchResult::GoDown(handle) => Vacant(VacantEntry {
key: key_seq.into(), key: key_seq.into(),
handle: HandleOrTree::Handle(handle.forget_node_type()), handle: HandleOrTree::Handle(handle),
_marker: PhantomData, _marker: PhantomData,
}), }),
search::SearchResult::Insert(key, handle) => Vacant(VacantEntry { search::SearchResult::Insert(key, handle) => Vacant(VacantEntry {
@ -1296,7 +1140,7 @@ mod borrow {
} }
} }
type Root<K, V> = NodeRef<marker::Owned, K, V, marker::Internal>; type Root<K, V> = NodeRef<marker::Owned, K, V>;
struct Tree<K, V> { struct Tree<K, V> {
root: Option<Root<K, V>>, root: Option<Root<K, V>>,
@ -1309,7 +1153,7 @@ impl<'a, K: core::fmt::Debug + 'a, V: core::fmt::Debug + 'a> core::fmt::Debug fo
fn format_node_ref<'a, K: 'a, V: 'a>( fn format_node_ref<'a, K: 'a, V: 'a>(
f: &mut core::fmt::Formatter<'_>, f: &mut core::fmt::Formatter<'_>,
node: &NodeRef<marker::Immut<'a>, K, V, marker::LeafOrInternal>, node: &NodeRef<marker::Immut<'a>, K, V>,
) -> core::fmt::Result ) -> core::fmt::Result
where where
K: core::fmt::Debug, K: core::fmt::Debug,
@ -1351,7 +1195,7 @@ impl<'a, K: core::fmt::Debug + 'a, V: core::fmt::Debug + 'a> core::fmt::Debug fo
Some(ref root) => { Some(ref root) => {
map.key(&"root").value_with(|f| { map.key(&"root").value_with(|f| {
let internal = root.reborrow(); let internal = root.reborrow();
format_node_ref(f, &internal.as_leaf_or_internal()) format_node_ref(f, &internal)
}); });
map.finish() map.finish()
@ -1420,12 +1264,7 @@ where
K: Ord, K: Ord,
{ {
fn as_subtree_mut<'a>(&'a mut self) -> Option<subtree::Subtree<K, V, marker::Mut<'a>>> { fn as_subtree_mut<'a>(&'a mut self) -> Option<subtree::Subtree<K, V, marker::Mut<'a>>> {
let root = self let root = self.root.as_mut()?.borrow_mut().dormant();
.root
.as_mut()?
.borrow_mut()
.dormant()
.as_leaf_or_internal();
Some(subtree::Subtree { Some(subtree::Subtree {
root: unsafe { root.awaken() }, root: unsafe { root.awaken() },
@ -1493,9 +1332,9 @@ mod tests {
} }
} }
let mut leaf = NodeRef::<_, (), Test, _>::new_leaf(); let mut leaf = NodeRef::<_, (), Test>::new();
leaf.borrow_mut().as_leaf_mut().value = Some(Test("test")); leaf.borrow_mut().as_leaf_mut().value = Some(Test("test"));
let mut root = NodeRef::new_leaf(); let mut root = NodeRef::new();
let mut leaf = leaf.reparent(unsafe { Handle::new_edge(root.borrow_mut(), 0) }, ()); let mut leaf = leaf.reparent(unsafe { Handle::new_edge(root.borrow_mut(), 0) }, ());