Reputation: 1703
I have just started learning about macros in elixir. I am currently reading the metaprogramming-elixir book.
Right at the start of the book there is an example of how to create a macro called say. This macro will take an expression like 5 + 5
and return a string of "5 plus 5 is 10"
...
defmacro say({:+, _, [lhs, rhs]}) do
quote do
lhs = unquote(lhs)
rhs = unquote(rhs)
result = lhs + rhs
IO.puts "#{lhs} plus #{rhs} is #{result}"
result
end
end
I am wondering why we need to use the quote
and unquote
macros when we are defining our own macro?
defmacro say({:+, _, [lhs, rhs]}) do
result = lhs * rhs
IO.puts "#{lhs} plus #{rhs} is #{result}"
result
end
Wouldn't the second version of the macro return the exact same answer?
Is there something that I am misunderstanding with the way macros work?
Upvotes: 1
Views: 408
Reputation: 121000
Macros are supposed to return AST. AST will be injected directly into the place where the call to macro was made from. This will happen during compilation stage.
That said, the latter will evaluate the result of the multiplication, put the message to stdout
during compilation stage and inject a constant, representing the result, in place of the macro call. This macro would accept only compile-time constants, it won’t accept e.g. variables:
say(5 + 5) # works
with foo <- 5, do: say(foo + 5) # raises
The former will produce an actual AST for evaluation.
Upvotes: 1