How do you convert Vec<&mut T> to Vec<&T>?

前端 未结 2 1589
渐次进展
渐次进展 2020-12-21 06:15

I\'ve got a vector of mutable references:

struct T;
let mut mut_vec: Vec<&mut T> = vec![];

相关标签:
2条回答
  • 2020-12-21 06:32

    If you need to actually convert, see Joe Clay's answer. However, you might not need to convert in the first place!

    Instead of changing the argument, change the function so that it accepts both mutable and immutable references. Here we use Borrow to abstract over both:

    use std::borrow::Borrow;
    
    fn main() {
        let mut st = String::new();
    
        let mut_vec = vec![&mut st];
        cool_func(mut_vec);
    
        let immut_vec = vec![&st];
        cool_func(immut_vec);
    }
    
    fn cool_func<S>(_: Vec<S>)
    where
        S: Borrow<String>,
    {
    }
    

    See also:

    • How to pass Iterator<String> as Iterator<&str>?
    • Why is it discouraged to accept a reference to a String (&String), Vec (&Vec), or Box (&Box) as a function argument?
    0 讨论(0)
  • 2020-12-21 06:35

    You can dereference and reborrow the mutable references, then add them to a new Vec:

    fn main() {
        let mut st = String::new();
    
        let mut_vec = vec![&mut st];
        let immut_vec = mut_vec.into_iter().map(|x| &*x).collect();
    
        cool_func(immut_vec);
    }
    
    fn cool_func(_: Vec<&String>) {}
    

    Note however, that this consumes the original Vec - you can't really get around this, as if the original Vec still existed, you'd have both mutable and immutable references to the same piece of data, which the compiler will not allow.

    0 讨论(0)
提交回复
热议问题