GranularId

Struct GranularId 

Source
pub struct GranularId<T> { /* private fields */ }
Expand description

The data type GranularId represents any ID which can have an arbitrary granularity, meaning that there is indefinitely many GranularIds in-between any two GranularIds. It is best used with unsized integer types such as u8, u16, u32, u64 and usize, but may be used with other data types implementing the required num_traits bounds.

An ID basically consists of multiple components

Implementations§

Source§

impl<T> GranularId<T>
where T: SequentialId,

Source

pub fn all_siblings(&self) -> SequentialIds<T>
where T: LowerBounded,

Gets all the siblings of this GranularId, ordered from the smallest sibling to the largest sibling. This is all the GranularIds which starts the same as this GranularId but has its last component changed.

use granular_id::GranularId;
let id = GranularId::from(vec![1u8, 2, 2]); // id 1.2.2
let mut all_siblings = id.all_siblings();
assert_eq!(all_siblings.next().unwrap(), vec![1, 2, 0].into()); // id 1.2.0
assert_eq!(all_siblings.next().unwrap(), vec![1, 2, 1].into()); // id 1.2.1
assert_eq!(all_siblings.next().unwrap(), vec![1, 2, 2].into()); // id 1.2.2
assert_eq!(all_siblings.next().unwrap(), vec![1, 2, 3].into()); // id 1.2.3
Source

pub fn next_siblings(&self) -> SequentialIds<T>
where T: CheckedAdd,

Gets all the next siblings of this GranularId, ordered from the smallest sibling larger than this ID to the largest sibling. This is all the GranularIds which starts the same as this GranularId but has its last component changed to any larger value.

use granular_id::GranularId;
let id = GranularId::from(vec![1u8, 2, 2]); // id 1.2.2
let mut next_siblings = id.next_siblings();
assert_eq!(next_siblings.next().unwrap(), vec![1, 2, 3].into()); // id 1.2.3
assert_eq!(next_siblings.next().unwrap(), vec![1, 2, 4].into()); // id 1.2.4
assert_eq!(next_siblings.next().unwrap(), vec![1, 2, 5].into()); // id 1.2.5
assert_eq!(next_siblings.next().unwrap(), vec![1, 2, 6].into()); // id 1.2.6
Source

pub fn children(&self) -> SequentialIds<T>
where T: LowerBounded,

Gets all direct children of this GranularId, ordered from the smallest child (which is larger than this ID, but smallest out of all children) to the largest child. This is all the GranularIds which starts with this GranularId but has one additional component.

use granular_id::GranularId;
let id = GranularId::from(vec![1u8, 2]); // id 1.2
let mut children = id.children();
assert_eq!(children.next().unwrap(), vec![1, 2, 0].into()); // id 1.2.0
assert_eq!(children.next().unwrap(), vec![1, 2, 1].into()); // id 1.2.1
assert_eq!(children.next().unwrap(), vec![1, 2, 2].into()); // id 1.2.2
assert_eq!(children.next().unwrap(), vec![1, 2, 3].into()); // id 1.2.3
Source§

impl<T> GranularId<T>

Source

pub fn previous_siblings(&self) -> BackSequentialIds<T>
where T: Bounded + One + Clone + CheckedSub,

Gets all the previous siblings of this GranularId, ordered from the largest sibling smaller than this ID to the smallest sibling. This is all the GranularIds which starts the same as this GranularId but has its last component changed to any smaller value.

use granular_id::GranularId;
let id = GranularId::from(vec![1u8, 2, 3]); // id 1.2.3
let mut previous_siblings = id.previous_siblings();
assert_eq!(previous_siblings.next().unwrap(), vec![1, 2, 2].into()); // id 1.2.2
assert_eq!(previous_siblings.next().unwrap(), vec![1, 2, 1].into()); // id 1.2.1
assert_eq!(previous_siblings.next().unwrap(), vec![1, 2, 0].into()); // id 1.2.0
assert_eq!(previous_siblings.next(), None); // No more smaller siblings
Source§

impl<T> GranularId<T>

Source

pub fn is_max_value(&self) -> bool

Checks whether this GranularId is the maximum value of this type. If it is, no other larger GranularIds exist of the same type.

use granular_id::GranularId;
let not_max: GranularId<u8> = vec![254].into();
let max: GranularId<u8> = vec![255].into();
assert!(!not_max.is_max_value());
assert!(max.is_max_value());
Source

pub fn granularity(&self) -> usize

Gets the granularity of this GranularId, which is the number of components it contains, or the “precision” it has


use granular_id::GranularId;
let id: GranularId<u8> = vec![1, 2, 3, 4].into(); // id 1.2.3.4, granularity 4
assert_eq!(id.granularity(), 4);
// Its children should have granularity 5:
assert_eq!(id.children().next().unwrap().granularity(), 5);
Source

pub fn is_root(&self) -> bool

Checks whether this GranularId is the root, which means not having any components.

use granular_id::GranularId;
let not_root: GranularId<u8> = vec![254].into();
let root: GranularId<u8> = vec![].into();
assert!(!not_root.is_root());
assert!(root.is_root());
Source

pub fn into_parent(self) -> Option<Self>

Turns this GranularId into its parent, that is, the same GranularId with the last component removed. If this GranularId is the root (has no components), this function returns the root. For a mutating version, see GranularId::pop, and for a copying version, see GranularId::parent. If this GranularId doesn’t have any components (is the root ID), this function returns None since the root ID doesn’t have a parent.

use granular_id::GranularId;
let id: GranularId<u8> = vec![1, 2, 3].into(); // id 1.2.3
assert_eq!(id.into_parent(), Some(vec![1, 2].into())); // id 1.2
Source

pub fn parent(&self) -> Option<Self>
where T: Clone,

Gets the parent of this GranularId, that is, the same GranularId with the last component removed. If this GranularId doesn’t have any components (is the root ID), this function returns None since the root ID doesn’t have a parent.

use granular_id::GranularId;
let id: GranularId<u8> = vec![1, 2, 3].into(); // id 1.2.3
assert_eq!(id.parent(), Some(vec![1, 2].into())); // id 1.2
Source

pub fn into_ancestors(self) -> Ancestors<T>

Returns an iterator over the ancestors of this GranularId. The iterator will yield all the ancestors, in order from the next-most parent until the root GranularId. This will give the same results as iteratively calling GranularId::parent. This function consumes the GranularId.

 use granular_id::GranularId;
 let id: GranularId<u8> = vec![1, 2, 3].into(); // id 1.2.3
 let mut ancestors = id.into_ancestors();
 assert_eq!(ancestors.next(), Some(vec![1, 2].into())); // id 1.2
 assert_eq!(ancestors.next(), Some(vec![1].into())); // id 1
 assert_eq!(ancestors.next(), Some(vec![].into())); // root id
 assert_eq!(ancestors.next(), None); // There are no more ancestors at this point
Source

pub fn ancestors(&self) -> Ancestors<T>
where T: Clone,

Returns an iterator over the ancestors of this GranularId. The iterator will yield all the ancestors, in order from the next-most parent until the root GranularId. This will give the same results as iteratively calling GranularId::parent.

 use granular_id::GranularId;
 let id: GranularId<u8> = vec![1, 2, 3].into(); // id 1.2.3
 let mut ancestors = id.ancestors();
 assert_eq!(ancestors.next(), Some(vec![1, 2].into())); // id 1.2
 assert_eq!(ancestors.next(), Some(vec![1].into())); // id 1
 assert_eq!(ancestors.next(), Some(vec![].into())); // root id
 assert_eq!(ancestors.next(), None); // There are no more parents at this point
Source

pub fn pop(&mut self) -> Option<T>

Removes the last component of this GranularId. To get the parent of any GranularId without mutating it, see GranularId::parent. The function returns the component popped, akin to Vec::pop, which is None if this GranularId doesn’t have a parent. In that case, this GranularId will remain unchanged as the root.

use granular_id::GranularId;
let mut id: GranularId<u8> = vec![1, 2, 3].into(); // id 1.2.3
assert_eq!(id.pop(), Some(3)); // popping the last component '3'
assert_eq!(id, vec![1, 2].into()); // id 1.2
Source

pub fn push(&mut self, component: T)

Pushes a new component to the GranularId, adding it as a new last component. Since the maximum bound for a GranularId of type T is [T::max], if any component is pushed to such an ID, the call doesn’t do anything.

use granular_id::GranularId;
let mut id: GranularId<u8> = vec![1, 2, 3].into(); // id 1.2.3
id.push(4);
assert_eq!(id, vec![1, 2, 3, 4].into()); // id 1.2.3.4
Source

pub fn pushing(&self, component: T) -> Self

Makes a new GranularId, adding the given component as its new last component. Since the maximum bound for a GranularId of type T is [T::max], if any component is pushed to such an ID, the call returns a plain copy of the original GranularId.

use granular_id::GranularId;
let mut id: GranularId<u8> = vec![1, 2, 3].into(); // id 1.2.3
assert_eq!(id.pushing(4), vec![1, 2, 3, 4].into()); // id 1.2.3.4
Source

pub fn append(&mut self, other: GranularId<T>)

Appends all components from another GranularId to this GranularId, adding them as a new last components. Since the maximum bound for a GranularId of type T is [T::max], if any components is appended to such an ID, the call doesn’t do anything.

use granular_id::GranularId;
let mut id: GranularId<u8> = vec![1, 2, 3].into(); // id 1.2.3
let id_2 = vec![4, 5, 6].into(); // id 4.5.6
id.append(id_2);
assert_eq!(id, vec![1, 2, 3, 4, 5, 6].into()); // id 1.2.3.4.5.6
Source

pub fn appending(&self, other: GranularId<T>) -> GranularId<T>

Makes a new GranularId, appending all components from another GranularId to that GranularId, adding them as a new last components. Since the maximum bound for a GranularId of type T is [T::max], if any components is appended to such an ID, the call returns a copy of the original GranularId.

use granular_id::GranularId;
let mut id: GranularId<u8> = vec![1, 2, 3].into(); // id 1.2.3
let id_2 = vec![4, 5, 6].into(); // id 4.5.6
assert_eq!(id.appending(id_2), vec![1, 2, 3, 4, 5, 6].into()); // id 1.2.3.4.5.6
Source

pub fn append_vec(&mut self, other: Vec<T>)

Appends all components from a Vec to this GranularId, adding them as a new last components. Since the maximum bound for a GranularId of type T is [T::max], if any components is appended to such an ID, the call doesn’t do anything.

use granular_id::GranularId;
let mut id: GranularId<u8> = vec![1, 2, 3].into(); // id 1.2.3
id.append_vec(vec![4, 5, 6]);
assert_eq!(id, vec![1, 2, 3, 4, 5, 6].into()); // id 1.2.3.4.5.6
Source

pub fn appending_vec(&self, other: Vec<T>) -> GranularId<T>

Makes a new GranularId, appending all components from a Vec to that GranularId, adding them as a new last components. Since the maximum bound for a GranularId of type T is [T::max], if any components is appended to such an ID, the call returns a copy of the original GranularId.

use granular_id::GranularId;
let mut id: GranularId<u8> = vec![1, 2, 3].into(); // id 1.2.3
assert_eq!(id.appending_vec(vec![4, 5, 6]), vec![1, 2, 3, 4, 5, 6].into()); // id 1.2.3.4.5.6
Source

pub fn root() -> Self

Gets the root GranularId of any type, that is, a GranularId without any components. That GranularId is the smallest one of that type.

use granular_id::GranularId;
let id: GranularId<u8> = GranularId::root(); // id <root>
assert_eq!(Into::<Vec<u8>>::into(id), vec![]);

Trait Implementations§

Source§

impl<T: Clone> Clone for GranularId<T>

Source§

fn clone(&self) -> GranularId<T>

Returns a duplicate of the value. Read more
1.0.0 · Source§

fn clone_from(&mut self, source: &Self)

Performs copy-assignment from source. Read more
Source§

impl<T: Debug> Debug for GranularId<T>

Source§

fn fmt(&self, f: &mut Formatter<'_>) -> Result

Formats the value using the given formatter. Read more
Source§

impl<T: Default> Default for GranularId<T>

Source§

fn default() -> GranularId<T>

Returns the “default value” for a type. Read more
Source§

impl<T: Display> Display for GranularId<T>

Source§

fn fmt(&self, f: &mut Formatter<'_>) -> Result

A GranularId is displayed similarly to a version string, where the GranularId created from the vector [1, 2, 3] is displayed as 1.2.3. If the GranularId is the root ID (doesn’t have any components), it is displayed as <root>.

Source§

impl<T> From<&[T]> for GranularId<T>

Source§

fn from(other: &[T]) -> Self

A slice of components may be turned into a GranularId. Keep in mind that the maximum GranularId of any type T is the one containing just the component T::max, attempting to convert any vector starting with T::max will result in the upper bound GranularId for that type.

Source§

impl<T> From<GranularId<T>> for Vec<T>

Source§

fn from(other: GranularId<T>) -> Vec<T>

Turns a GranularId into a vector of its components.

Source§

impl<T> From<Vec<T>> for GranularId<T>

Source§

fn from(other: Vec<T>) -> Self

A vector of components may be turned into a GranularId. Keep in mind that the maximum GranularId of any type T is the one containing just the component T::max, attempting to convert any vector starting with T::max will result in the upper bound GranularId for that type.

Source§

impl<T: Hash> Hash for GranularId<T>

Source§

fn hash<__H: Hasher>(&self, state: &mut __H)

Feeds this value into the given Hasher. Read more
1.3.0 · Source§

fn hash_slice<H>(data: &[Self], state: &mut H)
where H: Hasher, Self: Sized,

Feeds a slice of this type into the given Hasher. Read more
Source§

impl<T> IntoIterator for GranularId<T>

Source§

fn into_iter(self) -> Self::IntoIter

Turns this GranularId into an iterator over its components, consuming them.

Source§

type Item = T

The type of the elements being iterated over.
Source§

type IntoIter = <Vec<T> as IntoIterator>::IntoIter

Which kind of iterator are we turning this into?
Source§

impl<T> LowerBounded for GranularId<T>

Source§

fn min_value() -> Self

The lower bound for any GranularId (the smallest ID) is the empty ID which contains no components.

Source§

impl<T> Ord for GranularId<T>
where T: Ord,

Source§

fn cmp(&self, other: &Self) -> Ordering

When comparing two GranularIds, their relative positioning is determined by its first non-matching component. All ID:s starting with 1 is less than all ID:s starting with a 2 and 1.2 is ordered before 1.2.0. Here is an example of some ordered GranularIds:

use num_traits::bounds::LowerBounded;
use granular_id::GranularId;
let vec: Vec<GranularId<u8>> = vec![
    vec![1].into(),         // id 1
    vec![1, 0].into(),      // id 1.0
    vec![1, 1].into(),      // id 1.1
    vec![1, 1, 0].into(),   // id 1.1.0
    vec![1, 1, 1].into(),   // id 1.1.1
    vec![1, 1, 2].into(),   // id 1.1.2
    vec![1, 2].into(),      // id 1.2
    vec![2].into(),         // id 2
];
let mut min = GranularId::min_value();
for id in vec {
    assert!(id > min);
    min = id;
}

For a GranularId to have a total ordering, the component type must also have a total ordering.

1.21.0 · Source§

fn max(self, other: Self) -> Self
where Self: Sized,

Compares and returns the maximum of two values. Read more
1.21.0 · Source§

fn min(self, other: Self) -> Self
where Self: Sized,

Compares and returns the minimum of two values. Read more
1.50.0 · Source§

fn clamp(self, min: Self, max: Self) -> Self
where Self: Sized,

Restrict a value to a certain interval. Read more
Source§

impl<T: PartialEq> PartialEq for GranularId<T>

Source§

fn eq(&self, other: &GranularId<T>) -> bool

Tests for self and other values to be equal, and is used by ==.
1.0.0 · Source§

fn ne(&self, other: &Rhs) -> bool

Tests for !=. The default implementation is almost always sufficient, and should not be overridden without very good reason.
Source§

impl<T> PartialOrd for GranularId<T>
where T: Ord,

Source§

fn partial_cmp(&self, other: &Self) -> Option<Ordering>

Since GranularIds does have a total ordering if and only if its type has a total ordering, this function never returns None and just returns the value GranularId<T>::cmp would return

1.0.0 · Source§

fn lt(&self, other: &Rhs) -> bool

Tests less than (for self and other) and is used by the < operator. Read more
1.0.0 · Source§

fn le(&self, other: &Rhs) -> bool

Tests less than or equal to (for self and other) and is used by the <= operator. Read more
1.0.0 · Source§

fn gt(&self, other: &Rhs) -> bool

Tests greater than (for self and other) and is used by the > operator. Read more
1.0.0 · Source§

fn ge(&self, other: &Rhs) -> bool

Tests greater than or equal to (for self and other) and is used by the >= operator. Read more
Source§

impl<T> UpperBounded for GranularId<T>
where T: UpperBounded,

Source§

fn max_value() -> Self

The upper bound for any GranularId (the largest ID) is the empty ID which contains one component, containing the upper bound of the component type.

Source§

impl<T: Eq> Eq for GranularId<T>

Source§

impl<T> StructuralPartialEq for GranularId<T>

Auto Trait Implementations§

§

impl<T> Freeze for GranularId<T>

§

impl<T> RefUnwindSafe for GranularId<T>
where T: RefUnwindSafe,

§

impl<T> Send for GranularId<T>
where T: Send,

§

impl<T> Sync for GranularId<T>
where T: Sync,

§

impl<T> Unpin for GranularId<T>
where T: Unpin,

§

impl<T> UnwindSafe for GranularId<T>
where T: UnwindSafe,

Blanket Implementations§

Source§

impl<T> Any for T
where T: 'static + ?Sized,

Source§

fn type_id(&self) -> TypeId

Gets the TypeId of self. Read more
Source§

impl<T> Borrow<T> for T
where T: ?Sized,

Source§

fn borrow(&self) -> &T

Immutably borrows from an owned value. Read more
Source§

impl<T> BorrowMut<T> for T
where T: ?Sized,

Source§

fn borrow_mut(&mut self) -> &mut T

Mutably borrows from an owned value. Read more
Source§

impl<T> CloneToUninit for T
where T: Clone,

Source§

unsafe fn clone_to_uninit(&self, dest: *mut u8)

🔬This is a nightly-only experimental API. (clone_to_uninit)
Performs copy-assignment from self to dest. Read more
Source§

impl<T> From<T> for T

Source§

fn from(t: T) -> T

Returns the argument unchanged.

Source§

impl<T, U> Into<U> for T
where U: From<T>,

Source§

fn into(self) -> U

Calls U::from(self).

That is, this conversion is whatever the implementation of From<T> for U chooses to do.

Source§

impl<T> ToOwned for T
where T: Clone,

Source§

type Owned = T

The resulting type after obtaining ownership.
Source§

fn to_owned(&self) -> T

Creates owned data from borrowed data, usually by cloning. Read more
Source§

fn clone_into(&self, target: &mut T)

Uses borrowed data to replace owned data, usually by cloning. Read more
Source§

impl<T> ToString for T
where T: Display + ?Sized,

Source§

fn to_string(&self) -> String

Converts the given value to a String. Read more
Source§

impl<T, U> TryFrom<U> for T
where U: Into<T>,

Source§

type Error = Infallible

The type returned in the event of a conversion error.
Source§

fn try_from(value: U) -> Result<T, <T as TryFrom<U>>::Error>

Performs the conversion.
Source§

impl<T, U> TryInto<U> for T
where U: TryFrom<T>,

Source§

type Error = <U as TryFrom<T>>::Error

The type returned in the event of a conversion error.
Source§

fn try_into(self) -> Result<U, <U as TryFrom<T>>::Error>

Performs the conversion.