[−][src]Module core_extensions::transparent_newtype
Contains the TransparentNewtype trait to enable safer transmutation between types.
Safety for Users
Given that T impls TransparentNewtype<Inner=I>.
It is always safe to convert from I to T directly.
It is always safe to convert from pointers to I,eg.:*const I,*mut I,&I,&mut I, to pointers to T (the same kind of pointer/reference). This also includes all smart pointers (Box,Rc,Arc,etc) in the standard library.
Transmuting a generic type C<I> to C<T> is not always safe ,because some may store a <I as SomeTrait>::AssocType instead of storing I directly. This has to be evaluated on an individual basis.
Example
Casting a Vec<T> to a Vec<Wrapper<T>>,to use its Debug implementation.
use core_extensions::{SelfOps,TransparentNewtype}; use std::fmt; pub struct DebugFromDisplay<T:?Sized>(pub T); impl<T:?Sized+fmt::Display> fmt::Debug for DebugFromDisplay<T>{ fn fmt(&self,f:&mut fmt::Formatter)->fmt::Result{ fmt::Display::fmt(&self.0,f) } } unsafe impl<T:?Sized> TransparentNewtype for DebugFromDisplay<T>{ type Inner=T; } fn vec_as<T>(v:&Vec<T>)->&Vec<DebugFromDisplay<T>>{ unsafe{ ::std::mem::transmute(v) } } let list=vec!["\"hello\"","\"world\""]; for elem in list.piped_ref(vec_as) { assert_eq!(elem.0,format!("{:?}",elem)); }
Example
A totally ordered 32 bit float.
use core_extensions::{SelfOps,TransparentNewtype}; pub struct TotalF32(pub f32); //Eq,Ord,PartialEq,PartialOrd impls not shown unsafe impl TransparentNewtype for TotalF32{ type Inner=f32; } fn vec_to(v:&mut Vec<f32>)->&mut Vec<TotalF32>{ unsafe{ ::std::mem::transmute(v) } } let mut list=vec![1.0,0.0,2.0]; // This avoids the problem with using sort_by_key , // in which the borrow can't be returned from the closure. list.piped_mut(vec_to).sort(); assert_eq!(list,vec![0.0,1.0,2.0]);
Traits
TransparentNewtype | Trait for |