Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to swap values from a multidimensional array in Rust?

Tags:

arrays

rust

Using a matrix (multidimensional fixed sized array) defined as [[f64; 4]; 4], is it possible to swap two values?

std::mem::swap(&mut matrix[i][k], &mut matrix[k][l]);

Gives the error:

error[E0499]: cannot borrow `matrix[..][..]` as mutable more than once at a time
   --> math_matrix.rs:100
    |
100 | std::mem::swap(&mut matrix[i][j], &mut matrix[k][l]);
    |                     ------------       ^^^^^^^^^^^^^^^- first borrow ends here
    |                     |                  |
    |                     |                  second mutable borrow occurs here
    |                     first mutable borrow occurs here

The only way I could figure out how to accomplish this was to use a temp value, e.g.:

macro_rules! swap_value {
    ($a_ref:expr, $b_ref:expr) => {
        {
            let t = *$a_ref;
            *$a_ref = *$b_ref;
            *$b_ref = t;
        }
    }
}

Then use:

swap_value!(&mut matrix[i][k], &mut matrix[maxj][k]);

Is there a better alternative?

like image 456
ideasman42 Avatar asked Oct 29 '22 16:10

ideasman42


1 Answers

You will need to split the outside layers using split_at_mut. This creates two disjoint mutable references which can then be individually swapped:

use std::mem;

fn main() {
    let mut matrix = [[42.0f64; 4]; 4];

    // instead of 
    // mem::swap(&mut matrix[0][1], &mut b[2][3]);

    let (x, y) = matrix.split_at_mut(2);
    mem::swap(&mut x[0][1], &mut y[0][3]);
    //                             ^-- Note that this value is now `0`!
}

In the most general case, you'll likely need to add some code to figure out where to split and in which order.

like image 79
Shepmaster Avatar answered Dec 22 '22 16:12

Shepmaster