SLog

Struct SLog 

Source
pub struct SLog<T: StableType + AsFixedSizeBytes> { /* private fields */ }
Expand description

Non-reallocating growing vector optimized for storing logs or history entries

Very similar to SVec, but internally does not perform reallocations nor moves of data. Instead, when the capacity is reached, a new block of stable memory (which here is called a Sector) is allocated and attached to the end of the current block. So, in some sense, this is a linked list, where each node can hold multiple elements.

T has to implement both StableType and AsFixedSizeBytes. SLog itself also implements these trait, which means that you can store it inside an another stable structure.

This data structure is “infinite” - it can handle up to u64::MAX elements.

SLog grows exponentially - each new Sector is twice as big as the previous one. But if the canister is short on stable memory, the newly created Sector may be shrunk, to be able to continue to grow.

It is well optimized when you access elements near the end (the most recently added). The further the element you access from the end, the worser the performance.

Implementations§

Source§

impl<T: StableType + AsFixedSizeBytes> SLog<T>

Source

pub fn new() -> Self

Creates a new SLog

Does not allocate any heap or stable memory.

Source

pub fn push(&mut self, it: T) -> Result<(), T>

Inserts a new element at the end of the SLog

May allocate a new Sector. If the canister is out of stable memory, will return Err with the element that was about to get inserted.

§Example
let mut log = SLog::new();

log.push(10u64).expect("Out of memory");
Source

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

Removes an element from the end of the SLog

If the SLog is empty, returns None. If it was the last element of the last Sector and there are more Sectors before it, the last Sector gets deallocated, freeing the memory.

Source

pub fn clear(&mut self)

Removes all elements from this SLog

Deallocates all Sectors, but the first one, freeing the memory.

Source

pub fn last(&self) -> Option<SRef<'_, T>>

Returns an immutable reference SRef to the last element of this SLog

If the SLog is empty, returns None.

§Example
let mut log = SLog::new();

log.push(10u64).expect("Out of memory");

assert_eq!(*log.last().unwrap(), 10);
Source

pub fn first(&self) -> Option<SRef<'_, T>>

Efficiently returns an immutable reference SRef to the first element of this SLog

If the SLog is empty, returns None.

§Example
let mut log = SLog::new();

log.push(10u64).expect("Out of memory");

assert_eq!(*log.first().unwrap(), 10);
Source

pub fn get(&self, idx: u64) -> Option<SRef<'_, T>>

Returns an immutable reference SRef to an element at the requested index

See also SLog::get_mut.

The closer the index to 0, the worser the performance of this call.

If the SLog is empty, returns None

Source

pub fn get_mut(&mut self, idx: u64) -> Option<SRefMut<'_, T>>

Returns a mutable reference SRefMut to an element at the requested index

See also SLog::get.

The closer the index to 0, the worser the performance of this call.

If the SLog is empty, returns None

Source

pub fn len(&self) -> u64

Returns the length of this SLog

Source

pub fn is_empty(&self) -> bool

Returns true if the length of this SLog is 0

Source

pub fn rev_iter(&self) -> SLogIter<'_, T>

Returns a back-to-front iterator over this SLog

This iterator contains elements from last to first.

§Example
let mut log = SLog::new();

for i in 0..100 {
    log.push(i).expect("Out of memory");
}

let mut i = 99;
for elem in log.rev_iter() {
    assert_eq!(*elem, i);
    i -= 1;
}
Source§

impl<T: StableType + AsFixedSizeBytes + Debug> SLog<T>

Source

pub fn debug_print(&self)

Prints sectored representation of this SLog

Useful for tests

Trait Implementations§

Source§

impl<T: StableType + AsFixedSizeBytes> AsFixedSizeBytes for SLog<T>

Source§

const SIZE: usize = 56usize

Size of self when encoded
Source§

type Buf = [u8; 56]

Buffer that is used to encode this value into
Source§

fn as_fixed_size_bytes(&self, buf: &mut [u8])

Encodes itself into a slice of bytes. Read more
Source§

fn from_fixed_size_bytes(buf: &[u8]) -> Self

Decodes itself from a slice of bytes. Read more
Source§

fn as_new_fixed_size_bytes(&self) -> Self::Buf

Encodes itself into a new Self::Buf of size == Self::SIZE
Source§

impl<T: StableType + AsFixedSizeBytes> Default for SLog<T>

Source§

fn default() -> Self

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

impl<T: StableType + AsFixedSizeBytes> Drop for SLog<T>

Source§

fn drop(&mut self)

Executes the destructor for this type. Read more
Source§

impl<T: StableType + AsFixedSizeBytes> StableType for SLog<T>

Source§

unsafe fn stable_drop_flag_off(&mut self)

Sets stable drop flag to off position, if it is applicable Read more
Source§

unsafe fn stable_drop_flag_on(&mut self)

Should set stable drop flag to on position, if it is applicable Read more
Source§

fn should_stable_drop(&self) -> bool

Should return the value of the stable drop flag
Source§

unsafe fn stable_drop(&mut self)

Performs stable drop, releasing all underlying stable memory of this data structure Read more

Auto Trait Implementations§

§

impl<T> Freeze for SLog<T>

§

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

§

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

§

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

§

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

§

impl<T> UnwindSafe for SLog<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> AsDynSizeBytes for T

Source§

fn as_dyn_size_bytes(&self) -> Vec<u8>

Encodes self into vector of bytes Read more
Source§

fn from_dyn_size_bytes(buf: &[u8]) -> T

Decodes self from a slice of bytes. 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> 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> Same for T

Source§

type Output = T

Should always be Self
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.