Struct freezebox::FreezeBox

source ·
pub struct FreezeBox<T> { /* private fields */ }
Expand description

FreezeBox is a deref-able lazy-initialized container.

A FreezeBox<T> can have two possible states:

  • uninitialized: deref is not allowed.
  • initialized: deref to a &T is possible.

To upgrade a FreezeBox to the initialized state, call lazy_init. lazy_init does not require a mutable reference, making FreezeBox suitable for sharing objects first and initializing them later.

Panics

Attempting to lazy_init more than once, or deref while uninitialized will cause a panic.

Examples

This example creates a shared data structure, then initializes a member variable later.

use freezebox::FreezeBox;
use std::sync::Arc;

/// A data structure that we will initialize late.
#[derive(Default)]
struct Resources {
    name: FreezeBox<String>
}

// Create an instance of the `Resources` struct, which contains an
// uninitialized `name` field.
let resources = Arc::new(Resources::default());

// Clone the Arc to emulate sharing with other threads, contexts,
// or data structures.
let res2 = resources.clone();

// Here we emulate another thread accessing the shared data structure.
// NOTE: it's still our responsibility to ensure that the FreezeBox
// is initialized before anyone dereferences it.
//
let func = move || {
    // explicit deref
    assert_eq!(*res2.name, "Hello!");
    // implicit deref allows transparent access to inner methods
    assert_eq!(res2.name.len(), 6);
};

resources.name.lazy_init("Hello!".to_string());
func();

Implementations§

source§

impl<T> FreezeBox<T>

source

pub fn new(val: Option<T>) -> Self

Create a new FreezeBox with optional initialization.

A pre-inititialized FreezeBox<T> may not seem very useful, but it can be convenient when interacting with structs or interfaces that require a FreezeBox, e.g. unit tests.

To always create an uninitialized FreezeBox, use FreezeBox::default().

source

pub const fn const_default() -> Self

Create a new FreezeBox in const context

This is the same as FreezeBox::default except that it works in const context, which is desirable for global static singleton objects.

Examples
static X: FreezeBox<String> = FreezeBox::const_default();
X.lazy_init("hello".to_string());
assert_eq!(*X, "hello");
source

pub fn lazy_init(&self, val: T)

Initialize a FreezeBox.

The new value will be stored on the heap.

Panics

lazy_init will panic if the FreezeBox is already initialized. If it panics, the input value will be dropped.

source

pub fn is_initialized(&self) -> bool

Test whether a FreezeBox is initialized.

source

pub fn into_inner(self) -> Option<T>

Consume the FreezeBox and return its contents.

Trait Implementations§

source§

impl<T> Default for FreezeBox<T>

source§

fn default() -> Self

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

impl<T> Deref for FreezeBox<T>

§

type Target = T

The resulting type after dereferencing.
source§

fn deref(&self) -> &Self::Target

Dereferences the value.
source§

impl<T> Drop for FreezeBox<T>

source§

fn drop(&mut self)

Executes the destructor for this type. Read more

Auto Trait Implementations§

§

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

§

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

§

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

§

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

§

impl<T> UnwindSafe for FreezeBox<T>where T: UnwindSafe + RefUnwindSafe,

Blanket Implementations§

source§

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

source§

fn type_id(&self) -> TypeId

Gets the TypeId of self. Read more
source§

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

source§

fn borrow(&self) -> &T

Immutably borrows from an owned value. Read more
source§

impl<T> BorrowMut<T> for Twhere 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 Twhere 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, U> TryFrom<U> for Twhere U: Into<T>,

§

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 Twhere U: TryFrom<T>,

§

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.