Why the variable is not modified inside a function with suffix "!"

Dear Julia community,

I am trying to use the “!” prefix in order to modify a variable inside a function and have made this little test:

function test_copy!(a,b)
   a = b
   println("a in function: $a")
end

a = 0.0; b = 1.0;
test_copy!(a,b)
println("a outside function: $a")

The results are: “a in function: 1.0” and “a outside function: 0.0”.
So the variable a has not been modified by the call to test_copy!.

But if I do the same test with size(1) arrays

function test_equal_arrays!(vec,x)
   vec[1] = x
end

vec = [0.0]; x = 1.0
test_equal_arrays!(vec,x)
@show(vec)

I get “vec = [1.0]”.

So I am getting a little confused. Does someone knows how the “!” prefix work in that case ?
Thanks to all

The exclamation mark doesn’t do any work at all, it’s just a naming convention.

The difference between the two cases is that in the first case you just create a new local binding for the variable name a. In the second case you update the content of the mutable object that vec points to.

6 Likes

Nitpicking here, but the ! in foo!() is actually a postfix. This had me confused when I first read your title.

3 Likes

Ho thanks, I didn’t realise it was only a convention!

You’re right I’ll modify it !

Nitpicking here, XD, but the ! in foo!() is actually a suffix, because the character makes part of the token and it is not a separate operator.

5 Likes

Dammit, Jesus was right about that whole casting the first stone thing :rofl:

4 Likes

About the difference between bindings and modifying mutable objects, there were many questions about it here in this forum, I selected some of my previous answers:

1 Like

The confusing thing is that the equal sign in x[1] = 2 has absolutely nothing to do with the equal sign in x = 2. For instance you can see with x = randn(2); @which x[1] = 2 that this actually gets lowered to a function call.

3 Likes

The title was revised again :stuck_out_tongue: