[SOLVED] Bug? vec![] macro weirdness with Arc/Rc

#1

Is this what is expected from the vec! macro? I would expect it to have the same behavior as the loop.

use std::sync::Arc;
use std::sync::atomic::{AtomicUsize, Ordering};

pub fn main() {

    let count = 4;
    let v1 = vec![Arc::new(AtomicUsize::new(0)); count];
    
    let mut v2 = vec![];
    for _ in 0..count {
        v2.push(Arc::new(AtomicUsize::new(0)));
    }
    
    v1[0].store(42, Ordering::SeqCst);
    v2[0].store(42, Ordering::SeqCst);
    
    println!("{:?}", v1);
    println!("{:?}", v2);
    
}

(Playground)

Output:

[42, 42, 42, 42]
[42, 0, 0, 0]

Errors:

   Compiling playground v0.0.1 (/playground)
    Finished dev [unoptimized + debuginfo] target(s) in 0.81s
     Running `target/debug/playground`

1 Like

#2

vec![value; count] will clone the value, and for Arc that means they’ll end up sharing the same instance. Your for loop is creating multiple distinct Arc values instead.

The documentation also mentions this:

This will use clone to duplicate an expression, so one should be careful using this with types having a nonstandard Clone implementation. For example, vec![Rc::new(1); 5] will create a vector of five references to the same boxed integer value, not five references pointing to independently boxed integers.

3 Likes

#3

I see. Thanks! Should have looked in the docs first :slight_smile:

0 Likes