3

Given the following code:

a = true # let's assign `a` a value

# and let's test if calling `b`, an unassigned variable, throws an error
begin
  puts "The value of b is: #{b.inspect}"
rescue NameError => e
  puts "Caught an error: #{e}"
end

a || b = true # the assignment should never be executed because `a` is `true`

puts "The value of b is: #{b.inspect}" # will calling `b` still raise an error?

We get the following result:

Caught an error: undefined local variable or method `b' for main:Object
The value of b is: nil

Even though we expected calling b to raise an error the second time, we see that b is now, in fact, nil.

Why is that? Why does b get assigned nil? Since the || never reached the assignment, I would expect b to remain undefined. How can it be defined, but not assigned a value?

1 Answer 1

5

Some of the docs explain how variables are created; the explanation as I understand it is that's just how the parser works:

The local variable is created when the parser encounters the assignment, not when the assignment occurs:

a = 0 if false # does not assign to a
p local_variables # prints [:a]
p a # prints nil

You can see other examples of this:

b = true if false # b is nil
"test" || c = true # c is nil

And others it doesn't get assigned:

puts d if false # d generates a NameError
Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.