Spooky action at distance not applicable to vectors?

Here’s a simplified version of your original code:

x = 0
v = [0]

let
    global x = 1 # global needed here
    v[1] = 1     # no global needed here
end

So the question is why is global needed to assign to x but not to assign to v[1]. The answer is because x is a variable and v[1] is not a variable—it’s a location in an array. The former is assignment (x =) and the latter is mutation (v[i] =)—you’re just doing different things with different syntaxes. The former requires global to affect a global variable from a local scope. The latter modifies the contents of an array and there’s no such thing as a global or local array, an array is just an array; it may be accessible by a global variable and/or a local variable (often both, e.g. if a global is passed as an argument); modifying it via either is the same and neither requires annotation.

Here’s a variation of your code with three different behaviors:

x = 0
y = [0]
z = [0]

let
    global x = 1   # global needed here
    global y = [1] # global also needed here
    z[1] = 1       # no global needed here
end

In this version:

  • x is changed from referring to the value 0 to the value 1; global is required here
  • y is also changed from referring to the vector [0] to referring to a new vector [1]; global is also required here
  • z refers to the same vector the whole time, but the content of the vector is modified; global is not required here

You only need global in order to change what value a global variable refers to from a local scope. Modifying the content of a value has no relation to scope and it doesn’t matter whether the value being modified is accessed via a global variable or a local variable; indeed, it would be incoherent to distinguish the two since the same value can be accessed via a local or a global. Regarding this last point, consider this example:

g = [0]

let
    # modify array via global variable
    g[1] = 1
end

let
    # modify the same array via local variable
    l = g
    l[1] = 2
end

By the logic that g is global and l is local you would want a global annotation on the former and not require it on the latter, but that makes no sense because both operations are doing the same thing and modifying the same array. Arrays are not global or local, only variables are.

15 Likes