[−][src]Function inplace_it::inplace_array_uninitialized
pub unsafe fn inplace_array_uninitialized<T, R, Consumer: FnOnce(&mut [T]) -> R>(
size: usize,
limit: usize,
consumer: Consumer
) -> R
inplace_array_uninitialized
is unsafe API which is being used by inplace_array
and
inplace_copy_of
internally.
It's trying to place an array of T
on the stack and pass the reference to it into the
consumer
closure.
size
argument sets the requested size of an array.
consumer
's result will be returned.
If the result of array of T
is more than limit
(or it's size is more than 4096)
then the vector will be allocated in the heap and will be passed as a
reference instead of stack-based fixed-size array.
Sometimes size of allocated array might be more than requested. For sizes larger than 32,
the following formula is used: roundUp(size/32)*32
. This is a simplification that used
for keeping code short, simple and able to optimize.
For example, for requested 50 item [T; 64]
will be allocated.
For 120 items - [T; 128]
and so on.
Note that rounding size up is working for fixed-sized arrays only. If function decides to allocate a vector then its size will be equal to requested.
Safety
It uses core::mem::uninitialized
under the hood so placed memory is not initialized
and it is not safe to use this directly. You it with care, please.
Also inplace_array_uninitialized
DO NOT drop
inplaced memory.
But this function is FAST because it haven't initializing overhead. Really.
Examples
use inplace_it::inplace_array_uninitialized; // For sizes <= 32 will be allocated exactly same size array for i in 1..32 { unsafe { inplace_array_uninitialized( i, //size of array 1024, // limit of allowed stack allocation in bytes |memory: &mut [usize]| { // consumer which will use our allocated array assert_eq!(memory.len(), i); } ); } } // For sizes > 32 an array may contains a little more items for i in (50..500).step_by(50) { unsafe { inplace_array_uninitialized( i, //size of array 2048, // limit of allowed stack allocation in bytes |memory: &mut [u16]| { // consumer which will use our allocated array let mut j = i / 32; if (i % 32) != 0 { j += 1; } j *= 32; assert_eq!(memory.len(), j); } ); } } // But if size of fixed-size array more than limit then vector of exact size will be allocated for i in (50..500).step_by(50) { unsafe { inplace_array_uninitialized( i, //size of array 0, // limit of allowed stack allocation in bytes |memory: &mut [usize]| { // consumer which will use our allocated array assert_eq!(memory.len(), i); } ); } }