What is the difference between foo(mut x:&mut T) and foo(x:&mut T)?


I think by writing
fn foo(x:&mut T)
, one can modify the value of x inside the function foo. That’s true in some cases. But in some other cases,
the compiler require me to write
fn foo(mut x:&mut T)
Could anyone tell me why?
I didn’t find the reason in the book “The Rust Programming Language”.


x: &mut T is a mutable reference pointing to some data, so you can modify this data using x, but this signature does not allow you to modify x itself, i.e. in this function x will always point to the same place in memory. mut x: &mut T on other hand allows you to modify x inside of the function (but it will stay the same outside of the function), so you can change where x will point.


I stumbled on this syntax by accident, and came to think of it like the const modifier in C++, the one which comes after the asterisk, but in reverse.
(In reverse since the default in C++ is mutable, and const is opt-in, while in Rust it’s the opposite).

In this C++ function, it’s allowed to mutate p locally, since it’s a local copy of a pointer (it won’t change anything outside the function and it usually makes sense only if you want to point it to something else to save a local variable):

void f(int* p, int* n1)
    p = n1;

But you can also forbid changing the local pointer copy (if for some reason you want to) by putting const after it

void f(int* const p, int* n1)
    p = n1; // compilation error

In Rust it’s the other way around - the default is immutability so you can’t change the local copy of the “pointer”, but you can ask it to be mutable if you want to point it to something else.

Equivalent examples here (although like I said it’s the opposite thing from C++ :grinning:) .

This one doesn’t compile

This one does compile due to the added mut