0

Why am I allowed to unwrap the Arc/Mutex mutably for the new_mat object, even if that was declared as immutable at the beginning of the function?

use std::{
    sync::{Arc, Mutex},
    thread::{self, JoinHandle},
};

const SIZE: usize = 15;
const THREADS: usize = 5;

fn double(M: Vec<Vec<i64>>) -> (Vec<Vec<i64>>, Vec<Vec<i64>>) {
    let new_mat = vec![vec![0; SIZE]; SIZE];
    let arc = Arc::new(Mutex::new(new_mat));
    let mat_arc = Arc::new(Mutex::new(M));

    let handles: Vec<JoinHandle<()>> = (0..THREADS)
        .map(|i| {
            let c = Arc::clone(&arc);
            let m = Arc::clone(&mat_arc);
            thread::spawn(move || {
                let mut k = i;
                while k < SIZE {
                    println!("Thread {} filling row {}", i, k);
                    let mut mx = c.lock().unwrap();
                    let mo = m.lock().unwrap();
                    for j in 0..SIZE {
                        mx[k][j] = mo[k][j] * 2;
                    }
                    k += THREADS;
                }
            })
        })
        .collect();

    for h in handles {
        h.join().unwrap();
    }

    (
        Arc::try_unwrap(mat_arc).unwrap().into_inner().unwrap(),
        Arc::try_unwrap(arc).unwrap().into_inner().unwrap(),
    )
}

fn main() {
    let mut count = 0;

    let mut M = vec![vec![0; SIZE]; SIZE];

    for i in 0..SIZE {
        for j in 0..SIZE {
            M[i][j] = count as i64;
            count += 1;
        }
    }

    let (M, new_mat) = double(M);
    println!("Original Matrix:");
    println!("{:?}", M);
    println!("Double  Matrix:");
    println!("{:?}", new_mat);
}
Shepmaster
  • 326,504
  • 69
  • 892
  • 1,159
antogilbert
  • 146
  • 1
  • 10
  • 1
    You transfer ownership of the `Vec` to the `Arc` / `Mutex`. Immutability is a property of the variable binding, not the value. – Shepmaster Jul 02 '21 at 15:00

0 Answers0