# Escaping in a macro

**URL:** <https://discourse.julialang.org/t/escaping-in-a-macro/14543>\
**Category:** General Usage\
**Created:** [September 4, 2018, 3:24pm UTC](https://discourse.julialang.org/t/escaping-in-a-macro/14543 "2018-09-04T15:24:11Z")\
**Posts on this page:** 20\
**Page:** 1

<div class="post-metadata">

**Author:** ![LaszloH](https://avatars.discourse-cdn.com/v4/letter/l/fbc32d/32.png) [@LaszloH](https://discourse.julialang.org/u/LaszloH)\
**Post date:** [September 4, 2018, 3:24pm UTC](https://discourse.julialang.org/t/escaping-in-a-macro/14543/1 "2018-09-04T15:24:11Z")

</div>

In the documentation of Julia v1.0 there is almost nothing about escaping in a macro. I tried a simple debug function, which can be inserted at critical points of a function. It should print an expression or variable name, and its current value. I defined a macro in a module, but I get weird messages (b = c =) at loading the module, and within a function only the last value of several calls to the macro is actually shown in REPL. If I type in REPL `@db(1+2)` or ` a = falses(2); @db(a)` I get the desired effects.

Could anyone point to relevant information or tell, how I such simple macro should be written?

```julia
module TestModule
export @db, f

macro db(x) # only works in REPL, single call in a line
    print(x," = ")
    return :($(esc(x)))
end

function f()
   b = falses(3)
   @db(b)
   c = trues(5)
   @db(c)
end

end

```

I tried to open a Julia issue about the need of improved documentation of esc(), and about its unexpected behavior, but the issue was immediately closed.

---

<div class="post-metadata">

**Author:** ![rdeits](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/rdeits/32/286_2.png) [@rdeits](https://discourse.julialang.org/u/rdeits)\
**Post date:** [September 4, 2018, 3:42pm UTC](https://discourse.julialang.org/t/escaping-in-a-macro/14543/2 "2018-09-04T15:42:44Z")

</div>

This isn’t really an escaping issue at all. Macros are source code transformations, and they get run _before your code executes_. As a result, your `print` statements are being run when the macro is run, during the parsing and lowering of your source code.

If you want the macro to actually cause something to be printed at run-time, then that `println` needs to be inside the expression that the macro returns.

---

<div class="post-metadata">

**Author:** ![korsbo](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/korsbo/32/15942_2.png) [@korsbo](https://discourse.julialang.org/u/korsbo)\
**Post date:** [September 4, 2018, 3:45pm UTC](https://discourse.julialang.org/t/escaping-in-a-macro/14543/3 "2018-09-04T15:45:56Z")

</div>

```julia
macro db(x)
    return quote
           println($"$x = ", $x)
    end
end

```

May be more what you are looking for in this particular case. But then again, this is basically `Base.@show`.

---

<div class="post-metadata">

**Author:** ![LaszloH](https://avatars.discourse-cdn.com/v4/letter/l/fbc32d/32.png) [@LaszloH](https://discourse.julialang.org/u/LaszloH)\
**Post date:** [September 4, 2018, 4:21pm UTC](https://discourse.julialang.org/t/escaping-in-a-macro/14543/4 "2018-09-04T16:21:34Z")

</div>

I tried to put more inside the escaped expression and around it, all gave various errors. Could you give an example, how it is done?

---

<div class="post-metadata">

**Author:** ![LaszloH](https://avatars.discourse-cdn.com/v4/letter/l/fbc32d/32.png) [@LaszloH](https://discourse.julialang.org/u/LaszloH)\
**Post date:** [September 4, 2018, 4:21pm UTC](https://discourse.julialang.org/t/escaping-in-a-macro/14543/5 "2018-09-04T16:21:36Z")

</div>

Thanks, but the listed macro does not work. It needs escaping, which the documentation does not tell, how to do.

---

<div class="post-metadata">

**Author:** ![korsbo](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/korsbo/32/15942_2.png) [@korsbo](https://discourse.julialang.org/u/korsbo)\
**Post date:** [September 4, 2018, 4:27pm UTC](https://discourse.julialang.org/t/escaping-in-a-macro/14543/6 "2018-09-04T16:27:35Z")

</div>

Aah, I had not tested my macro from within a function.

I think that

```julia
macro db(x)
    return esc(quote
           println($"$x = ", $x)
    end)
end

```

should do what you want.

But I, too, feel that I’m mostly trying things around until something works without a deep understanding. A deep and rigorous tutorial would be helpful.

---

<div class="post-metadata">

**Author:** ![korsbo](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/korsbo/32/15942_2.png) [@korsbo](https://discourse.julialang.org/u/korsbo)\
**Post date:** [September 4, 2018, 4:32pm UTC](https://discourse.julialang.org/t/escaping-in-a-macro/14543/7 "2018-09-04T16:32:42Z")

</div>

or the shorter:

```julia
macro db(x)
    return esc(:(println($"$x = ", $x)))
end
```

---

<div class="post-metadata">

**Author:** ![yuyichao](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/yuyichao/32/20_2.png) [@yuyichao](https://discourse.julialang.org/u/yuyichao)\
**Post date:** [September 4, 2018, 4:35pm UTC](https://discourse.julialang.org/t/escaping-in-a-macro/14543/8 "2018-09-04T16:35:41Z")

</div>

You should ESC x not the whole thing.  
In general you escape each input once and exactly once.

---

<div class="post-metadata">

**Author:** ![Tamas\_Papp](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/tamas_papp/32/25949_2.png) [@Tamas\_Papp](https://discourse.julialang.org/u/Tamas_Papp)\
**Post date:** [September 4, 2018, 4:42pm UTC](https://discourse.julialang.org/t/escaping-in-a-macro/14543/9 "2018-09-04T16:42:59Z")

</div>

You may find the source of [`Base.@show`](https://github.com/JuliaLang/julia/blob/c8450d862f0e2653011f68118daecfe12b398c90/base/show.jl#L551) instructive, it does something similar.

---

<div class="post-metadata">

**Author:** ![ExpandingMan](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/expandingman/32/866_2.png) [@ExpandingMan](https://discourse.julialang.org/u/ExpandingMan)\
**Post date:** [September 4, 2018, 4:46pm UTC](https://discourse.julialang.org/t/escaping-in-a-macro/14543/10 "2018-09-04T16:46:32Z")

</div>

If you are ever confused about what your macro is doing, remember to use `@macroexpand` to see the code that it will give (though I do wish the output of this were easier to ready).

---

<div class="post-metadata">

**Author:** ![LaszloH](https://avatars.discourse-cdn.com/v4/letter/l/fbc32d/32.png) [@LaszloH](https://discourse.julialang.org/u/LaszloH)\
**Post date:** [September 4, 2018, 4:46pm UTC](https://discourse.julialang.org/t/escaping-in-a-macro/14543/11 "2018-09-04T16:46:41Z")

</div>

> [@korsbo](#):
>
> return esc(:(println($"$x = ", $x)))

Thanks, Niklas! Your macros work. If only we get decent Julia documentation on these.

---

<div class="post-metadata">

**Author:** ![korsbo](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/korsbo/32/15942_2.png) [@korsbo](https://discourse.julialang.org/u/korsbo)\
**Post date:** [September 4, 2018, 4:49pm UTC](https://discourse.julialang.org/t/escaping-in-a-macro/14543/12 "2018-09-04T16:49:09Z")

</div>

Given the additional input we have received (thanks everyone!), we should maybe revise the macro to:

```julia
macro db(x)
    return :(println($"$x = ", $(esc(x))))
end

```

---

<div class="post-metadata">

**Author:** ![Tamas\_Papp](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/tamas_papp/32/25949_2.png) [@Tamas\_Papp](https://discourse.julialang.org/u/Tamas_Papp)\
**Post date:** [September 4, 2018, 4:54pm UTC](https://discourse.julialang.org/t/escaping-in-a-macro/14543/13 "2018-09-04T16:54:19Z")

</div>

> [@LaszloH](#):
>
> If only we get decent Julia documentation on these.

I would argue that the documentation is “decent”, even if it could be improved (which is generally true for most documentation).

Escaping is tricky (because it involves [hygiene](https://docs.julialang.org/en/stable/manual/metaprogramming/#Hygiene-1)), and more examples could always help, but most of the tools that were suggested in this topic are [documented with examples](https://docs.julialang.org/en/stable/manual/metaprogramming/#Building-an-advanced-macro-1).

---

<div class="post-metadata">

**Author:** ![LaszloH](https://avatars.discourse-cdn.com/v4/letter/l/fbc32d/32.png) [@LaszloH](https://discourse.julialang.org/u/LaszloH)\
**Post date:** [September 4, 2018, 5:24pm UTC](https://discourse.julialang.org/t/escaping-in-a-macro/14543/14 "2018-09-04T17:24:36Z")

</div>

Maybe the documentation is good for experts, like you guys, but for a novice user it is just confusing. E.g. I could not find a description of the construct $“…”. The function esc() is said to be " Only valid in the context of an `Expr` returned from a macro". It is not clear, we can use it in assignments to local variables. So, where is it allowed? And so on…

---

<div class="post-metadata">

**Author:** ![kristoffer.carlsson](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/kristoffer.carlsson/32/22_2.png) [@kristoffer.carlsson](https://discourse.julialang.org/u/kristoffer.carlsson)\
**Post date:** [September 4, 2018, 5:31pm UTC](https://discourse.julialang.org/t/escaping-in-a-macro/14543/15 "2018-09-04T17:31:38Z")

</div>

Interpolation is described in [https://docs.julialang.org/en/stable/manual/metaprogramming/#Interpolation-1](https://docs.julialang.org/en/stable/manual/metaprogramming/#Interpolation-1).

I would read through the whole chapter since just spot-reading a particular subsection will not give you the complete picture of meta-programming in Julia.

---

<div class="post-metadata">

**Author:** ![Tamas\_Papp](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/tamas_papp/32/25949_2.png) [@Tamas\_Papp](https://discourse.julialang.org/u/Tamas_Papp)\
**Post date:** [September 4, 2018, 5:39pm UTC](https://discourse.julialang.org/t/escaping-in-a-macro/14543/16 "2018-09-04T17:39:50Z")

</div>

> [@LaszloH](#):
>
> for a novice user it is just confusing

Macros are tricky, especially when it comes to hygiene. I agree that more documentation would be nice, especially in the form of tutorials, and I guess those will appear in due time now that we have a stable release.

Also, don’t underestimate what you can learn from just reading the source. `Base` and the standard libraries have examples of complex macros, usually written by people who know Julia well.

That said, perhaps a novice user should wait a while before writing macros. They are not at all essential to using the language and even writing complex and powerful libraries.

---

<div class="post-metadata">

**Author:** ![LaszloH](https://avatars.discourse-cdn.com/v4/letter/l/fbc32d/32.png) [@LaszloH](https://discourse.julialang.org/u/LaszloH)\
**Post date:** [September 4, 2018, 5:49pm UTC](https://discourse.julialang.org/t/escaping-in-a-macro/14543/17 "2018-09-04T17:49:18Z")

</div>

> I would read through the whole chapter

I did, and did not find any example or description of the construct $“…”. What did I miss?

> a novice user should wait a while before writing macros

Maybe, but such a simple thing as showing an expression and its value could be simple enough for a newb.

---

<div class="post-metadata">

**Author:** ![Tamas\_Papp](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/tamas_papp/32/25949_2.png) [@Tamas\_Papp](https://discourse.julialang.org/u/Tamas_Papp)\
**Post date:** [September 4, 2018, 5:58pm UTC](https://discourse.julialang.org/t/escaping-in-a-macro/14543/18 "2018-09-04T17:58:07Z")

</div>

> [@LaszloH](#):
>
> description of the construct $“…”. What did I miss?

The link above takes you there directly, so possibly that part?

> [@LaszloH](#):
>
> showing an expression and its value could be simple enough for a newb.

I am not sure I agree; perhaps you could show us a language where this is simple. Eg in C, it is [rather complex](https://gcc.gnu.org/onlinedocs/cpp/Stringizing.html#Stringizing), in Common Lisp it would be simpler than Julia because that language does not have hygiene by default (so more complex macros need to work around that).

I have not seen a language where macros of any kind are novice material.

---

<div class="post-metadata">

**Author:** ![Tero\_Frondelius](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/tero_frondelius/32/7629_2.png) [@Tero\_Frondelius](https://discourse.julialang.org/u/Tero_Frondelius)\
**Post date:** [September 4, 2018, 6:00pm UTC](https://discourse.julialang.org/t/escaping-in-a-macro/14543/19 "2018-09-04T18:00:03Z")

</div>

> [@LaszloH](#):
>
> Maybe, but such a simple thing as showing an expression and its value could be simple enough for a newb.

You are the best expert of missing documentation. Please make a pull request to propose a good example in the right place. However, be prepared to iterate because it seems that a lot of people have an opinion on this matter.

---

<div class="post-metadata">

**Author:** ![LaszloH](https://avatars.discourse-cdn.com/v4/letter/l/fbc32d/32.png) [@LaszloH](https://discourse.julialang.org/u/LaszloH)\
**Post date:** [September 4, 2018, 6:15pm UTC](https://discourse.julialang.org/t/escaping-in-a-macro/14543/20 "2018-09-04T18:15:13Z")

</div>

> The link above takes you there directly

I read that section, too thoroughly. It says that “Julia allows _interpolation_ of literals or expressions into quoted expressions. Interpolation is indicated by a prefix `$` .” Accordingly, (and those are the examples given) you can write $a, $(exp), and $:(expr).

There is nothing about the construct of $“…”. This is what I missed, or overlooked. What does it stand for?

[Next page](https://discourse.julialang.org/t/escaping-in-a-macro/14543.md?page=2)
