3
votes
for i in 1:2
    if i == 2
        print(x)
    end
    if i == 1
        x = 0
    end
end

UndefVarError : x not defined

Why does the code gives that error instead of printing 0 in julia?

While in python the following code print 0?

for i in range(2):
    if i==1:
        print(x)
    if i==0:
        x=0
2
No language will let you use a variable before you declare it. And x is undeclared. - user47589
the variable is not used before declaring it and this works in python - Erik Garcia
You're using it on line 3. Where are you declaring it? And no, this won't work in Python. Please open a Python prompt and type in print(x). You'll get NameError: name 'x' is not defined - user47589
@Amy: this actually will work in Python, because x is set to 0 on the first iteration of the loop and only printed on the second. - DSM
Julia has local scoping introduced by most code blocks. This is so that the compiler can optimise the functions easily. Check out this in the docs: docs.julialang.org/en/v0.6.2/manual/variables-and-scoping/… - niczky12

2 Answers

4
votes

The reason is because in the loop a variable gets a new binding each time a loop is executed, see https://docs.julialang.org/en/latest/manual/variables-and-scoping/#For-Loops-and-Comprehensions-1.

In fact while loop changed this behavior between Julia 0.6.3 and Julia 0.7 (in Julia 0.6.3 a new binding was not created). Therefore the following code:

function f()
    i=0
    while i < 2
        i+=1
        if i == 2
            print(x)
        end
        if i == 1
            x = 0
        end
    end
end

Gives the following output.

Julia 0.6.3

julia> function f()
           i=0
           while i < 2
               i+=1
               if i == 2
                   print(x)
               end
               if i == 1
                   x = 0
               end
           end
       end
f (generic function with 1 method)

julia> f()
0

Julia 0.7.0

julia> function f()
           i=0
           while i < 2
               i+=1
               if i == 2
                   print(x)
               end
               if i == 1
                   x = 0
               end
           end
       end
f (generic function with 1 method)

julia> f()
ERROR: UndefVarError: x not defined
Stacktrace:
 [1] f() at .\REPL[2]:6
 [2] top-level scope

For-loop created a new binding already in Julia 0.6.3 at each iteration so it fails both under Julia 0.6.3 and Julia 0.7.0.

EDIT: I have wrapped the examples in a function, but you would get the same result if you executed the while loop in global scope.

2
votes

Ignore my comment andgo with Bogumil's answer as that's is the real rwason why your x variable disapears in thesecond iteration.

If you want your code to work like in Python, you can add the global keyword to your assignment of x:

for i in 1:2
    if i == 2
        print(x)
    end
    if i == 1
        global x = 0
    end
end

Note that this is not recommended in most cases as it'll make your code performance suffer. Julia likes local variables that the compiler can optimise away easily.