Julia scoping: why does this function modify a global variable?

独自空忆成欢 提交于 2021-01-28 02:32:20

问题


I'm a relative newcomer to Julia, and so far I am a fan of it. But coming from years of R programming, some scoping rules leave me perplexed.

Let's take this function. This behaves exactly as I would expect.

function foo1(x)
    y = x
    t = 1
    while t < 1000
      t += 1
      y += 1
    end
    return 42
end

var = 0;
foo1(var)
# 42
var
# 0

But when doing something similar on an array, it acts as a mutating function (modifies it argument in the global scope!)

function foo2(x)
    y = x
    t = 1    
    while t < 1000
      t += 1
      y[1] += 1
    end
    return 42
end

var = zeros(1);
foo2(var)
# 42
var
# 999.0

I realize I can fix this by changing the first line to y = copy(x) , but what is the reason for such a (dangerous?) behaviour in the first place?


回答1:


I would write an answer to this, but I think John Myles White has already done it better than I ever could so I'll just link to his blogpost:

https://www.juliabloggers.com/values-vs-bindings-the-map-is-not-the-territory-3/

In short x = 1 and x[1] = 1 are very different operations. The first one is assignment—i.e. changing a binding of the variable x—while the second is a syntactic sugar for calling the setindex! function, which, in the case of arrays, assigns to a location in the array. Assignment only changes which variables refer to which objects and never modifies any objects. Mutation only modifies objects and never changes which variables refer to which objects. This answer has a bit more detail about the distinction: Creating copies in Julia with = operator.



来源:https://stackoverflow.com/questions/62534592/julia-scoping-why-does-this-function-modify-a-global-variable

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!