'Temporary value created when unwrap()
I'm trying to create a thread-safe version of a stack based on a vector.
The unsafe version (just a simplified example to focus in) is
fn top<'a, T>( v: &'a Vec<T> ) -> &'a T {
return & v[0];
} // ()
// --------------------------------------------
fn main() {
let mut v = Vec::<i32>::new();
v.push( 1234 );
println!( "{}", top( & v ) );
} // ()
But the safe version does not compile:
type SafeVec<T> = Arc< RwLock< Vec<T> > >;
// --------------------------------------------
fn new_safe_vec<T>() -> SafeVec<T> {
return Arc::new( RwLock::new( Vec::<T>::new() ) );
} // ()
// --------------------------------------------
fn top_safe<'a, T>( v: &'a SafeVec<T> ) -> &'a T {
return & v.read().unwrap()[0]; <------ returns a value referencing
<------ data owned by the current function
<------ (temporary crated here)
} // ()
// --------------------------------------------
fn main() {
} // ()
Does unwrap() create a temporary copy of the vector held inside? How to avoid it?
Solution 1:[1]
And, just for completeness, to avoid a copy we'll need to have a guarded reference to the cell. A trick could be using a macro so that the RwLockReadGuard is kept in main().
use std::sync::Arc;
use std::sync::RwLock;
// ==================================================================
type SafeVec<T> = Arc< RwLock< Vec<T> > >;
// ------------------------------------------------------------------
fn new_safe_vec<T>() -> SafeVec<T> {
return Arc::new( RwLock::new( Vec::<T>::new() ) );
} // ()
// ------------------------------------------------------------------
macro_rules! top_safe {
($v: expr) => {
$v.read().unwrap()[0]
} // ()
} // macro
// ==================================================================
fn main() {
let sv = new_safe_vec::<i32>();
sv.write().unwrap().push( 1234 );
println!( "{}", top_safe!( & sv ) );
} // ()
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
| Solution | Source |
|---|---|
| Solution 1 | cibercitizen1 |
