Why does Elixir allow closures with undefined variables?

I can understand this:

iex(7)> outside_val = 5 5 iex(8)> print = fn() -> IO.puts(outside_val) end #Function<20.90072148/0 in :erl_eval.expr/5> iex(9)> print.() 5 :ok 

What I am not getting so much is why Elixir allows you to define a print function, even if external_val is not defined and only an error later? It is not possible to go to 'external_val' after the constraint has been defined anyway, is it not better to check Elixir for the existence of the variable at creation time?

What I mean:

 iex(2)> print = fn () -> IO.puts(outside_val) end #Function<20.90072148/0 in :erl_eval.expr/5> iex(3)> outside_val = 5 5 iex(4)> print.() ** (RuntimeError) undefined function: outside_val/0 
+5
source share
2 answers

This is a bug in Elixir, which will be fixed in v1.1 (already in the main branch):

 Interactive Elixir (1.1.0-dev) - press Ctrl+C to exit (type h() ENTER for help) iex(1)> print = fn () -> IO.puts(outside_val) end ** (CompileError) iex:1: undefined function outside_val/0 

The current implementation delays the extension for calling the function in IEx.Helpers . In master, we simply import IEx.Helpers , so we no longer need to extend outside_val later.

+10
source

There are several steps when defining a function in Erlang (and in Elixir, since it is built on top of ErlangVM).

First, you tokenize the input:

 {ok, Ts, _} = erl_scan:string("fun() -> Z + 1 end."). 

Then you create an abstract syntax tree:

 {ok, [ListAST]} = erl_parse:parse_exprs(Ts). 

The final step is to evaluate it with:

 Bindings = [{'Z', 1}]. erl_eval:expr(ListAST, Bindings). 

In the last step, Erlang can see that there are undefined variables and throw an exception.

In Elixir, most of the language functions are implemented as macros, so the last step is not performed during function definition, but when it is called. I'm not sure if you can check if all the variables are connected inside the macro definition. If possible, it will be a cool solution.

+3
source

Source: https://habr.com/ru/post/1212936/


All Articles