Scripting Helpers is winding down operations and is now read-only. More info→
Ad
Log in to vote
5

How does Evaluation work in Lua?

Asked by 9 years ago

Short Circuiting

Now, when it comes to short-circuiting values, Lua does indeed short-circuit. For example:

01function hello()
02    print('hello')
03    return true
04end
05 
06function bye()
07    print('bye')
08    return false
09end
10 
11if(hello() or bye()) then
12    print('check to short-ciruit')
13end

hello

check to short-circuit

As you can see, the bye function was not called and thus that is proof that short-circuiting occurred. Now one way to get around this short-circuiting is to preferably set a reference to the function values before-hand.

For example:

01function hello()
02    print('hello')
03    return true
04end
05 
06function bye()
07    print('bye')
08    return false
09end
10 
11local x = hello()
12local y = bye()
13 
14if(x or y) then
15print('check to short-circuit')
16end

hello

bye

check to short-circuit

Now, as you can see in this example, both values from the hello and bye methods were printed.

I do understand how short-circuiting occurs when you only have simple conditional statements, but when you bring other factors involved, I'm still a bit addled on it. I want to know why setting the variables before hand makes a difference, and just a more clear explanation on how evaluation in Lua works. Any links too would be really appreciated.


My Question

How does evaluation in Lua work? Why did referring to the methods before-hand cause short-circuiting not to occur?

1
You are calling the bye function when you do y = bye() NotsoPenguin 705 — 9y
0
Yes, but when I just do 'bye()', I am also calling the bye() function. DigitalVeer 1473 — 9y
1
It does not cancel out anything. You called the bye function when you set the variable. Your if statement is actually just `if true or false` NotsoPenguin 705 — 9y
0
If my statement is just 'if true or false', then why does the print statement get called? DigitalVeer 1473 — 9y

1 answer

Log in to vote
7
Answered by
Unclear 1776 Moderation Voter
9 years ago

I want to know why setting the variables before hand makes a difference, and just a more clear explanation on how evaluation in Lua works.

Alright. I'll see what I can do.

Why setting the variables before hand makes a difference.

Short-circuit evaluation is when a later operation in a boolean statement is not evaluated because a previous operation in that same boolean statement is true. It is merely where the language does the minimal amount of evaluating to figure out the result of a boolean statement.

Note in a boolean statement. When point a variable to the result of an operation before the boolean statement happens, then the operation has already been evaluated.

There are no take backs in Lua; just because the result of that operation may evaluate to false in a later boolean statement, does not mean that the operation never happened.

Notice in your code...

01function hello()
02    print('hello')
03    return true
04end
05 
06function bye()
07    print('bye')
08    return false
09end
10 
11local x = hello()
12local y = bye()
13 
14if(x or y) then
15print('check to short-circuit')
16end

... you set x and y to the results of hello and bye. You know this because you wrote hello() and bye().

Notice that you called both of them. That means that those variables are now pointing to the evaluated results of the functions. You can check this by inserting a print statement between your local declarations and your if statement.

Remember that there are no take backs. This means that by the time you reached that if statement if (x or y) then, you already evaluated hello and bye. This means that naturally, those functions have already run once and printed out "hello" and "bye".

This is not a matter of short-circuiting, but more of a matter of you messing something up and attributing it to short-circuiting.

Basics

Evaluating boolean statements in Lua is as logical as it gets. Everything in Lua follows the standard properties of booleans, and there are no gotcha moments when working with Lua.

That being said, since you are asking this question, I'll give you a brief overview of how Lua works with boolean statements anyway.

The following will be considered false:

  • false

  • nil

  • Any variable pointing to false or nil

Everything else is true. That means that 0, "" or '' (empty strings), and {} (empty tables / data structures) will also evaluate as true, unlike in many other programming languages.

Here are some basic truth operations and their results...

01print(true and true) --> true
02print(true and false) --> false
03print(false and true) --> false
04print(false and false) --> false
05-- or returns true if BOTH statements are true
06-- or returns false if ONE or more statements are false
07 
08print(true or true) --> true
09print(true or false) --> true
10print(false or true) --> true
11print(false or false) --> false
12-- or returns true if ONE or more statements are true
13-- or returns false if BOTH statements are false
14 
15print(not true) --> false
16print(not false) --> true
17-- not returns the opposite of whatever is to the right of it
18-- not takes precedence before and/or operations.. so
19-- print(not true or false) will print false

Ternary

You may know that Lua does not have a true implementation of ternary operators. However, you can get by with a pseudo-ternary operation that Lua does support.

For most purposes, a and b or c will suffice. Lua will go from left to right and evaluate each statement. It will return the last statement in a combo of true statements connected by ands if the statement is true. Otherwise, it will keep going.

Here is an example...

01print(true or false) --> true
02-- notice how it is the last true statement
03 
04print(1 and 2 and 3 or false) --> 3
05-- 1 is true, 2 is true, and 3 is true.
06-- Notice how 3 is then followed by an or.
07-- This makes 3 the last true statement in a string of true statements.
08 
09print({} and 2 or true) --> 2
10-- {} is true and 2 is true.
11-- Same logic as above.
12-- Even through the next statement is true,
13-- 2 is the last true statement in a combo of true statements connected by ands.
14 
15print(1 and 2 and false or 3) --> 3
View all 21 lines...

Parenthesis

Note that parenthesis have a bit of priority. This means that Lua, when it encounters a parenthesis, first evaluates everything in the parenthesis before proceeding with evaluating the rest of the boolean statement. This means that you can have multiple short-circuiting effects and nested pseudo-ternary.

Here is an example...

1print(1 and (false or 2) or 0) --> 2
2-- 1 is true, but then we encounter a parenthesis.
3-- Let's evaluate it.
4-- false is false, so we look at the next statement which is just 2.
5-- So, our parenthesis returns 2.
6-- Our statement is simplified to...
7-- print(1 and 2 or 0)
8-- Since 2 is the last statement in the combo of ands, we will return 2.

Working with functions in boolean statements

Working with a function call is similar to working with parenthesis. First, you will evaluate what is in the function when you encounter it, similarly to how you would evaluate what is in a parenthesis. Then, you will proceed with the resulting value as you would regularly.

Here is an example...

01function a()
02    return 2
03end
04 
05print(false or a() and 3) --> 3
06-- Notice how false is false, so we go to the next statement.
07-- We encountered a function call a() so we will evaluate it.
08-- a() returns 2 so our statement is simplified to...
09-- print(false or 2 and 3)
10-- We proceed regularly since 2 is true, and return 3.
0
Haha, oops. Misremembered the definition of short-circuiting. adark 5487 — 9y
1
Really detailed explanation, Sukinahito. Though I do know my true/false combinations, at least it's helpful to people who may be new to it. Cheers, mate DigitalVeer 1473 — 9y
Ad

Answer this question