# Why do we need the \`do\` keyword?

**URL:** <https://discourse.julialang.org/t/why-do-we-need-the-do-keyword/22236>\
**Category:** Internals & Design\
**Created:** [March 23, 2019, 7:34am UTC](https://discourse.julialang.org/t/why-do-we-need-the-do-keyword/22236 "2019-03-23T07:34:21Z")\
**Posts on this page:** 14\
**Page:** 1

<div class="post-metadata">

**Author:** ![sagartewari01](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/sagartewari01/32/7810_2.png) [@sagartewari01](https://discourse.julialang.org/u/sagartewari01)\
**Post date:** [March 23, 2019, 7:34am UTC](https://discourse.julialang.org/t/why-do-we-need-the-do-keyword/22236/1 "2019-03-23T07:34:21Z")

</div>

According to the [documentation](https://docs.julialang.org/en/v1/base/base/#do), all this keyword does is create a lambda and insert it as the first argument of function call before it. This task could be accomplished with a macro with very similar syntax:

```julia
@do
map(coll) x -> x^2

```

I wanted to know the reason behind integrating this feature into the language as a keyword.

---

<div class="post-metadata">

**Author:** ![kevbonham](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/kevbonham/32/216165_2.png) [@kevbonham](https://discourse.julialang.org/u/kevbonham)\
**Post date:** [March 23, 2019, 9:13am UTC](https://discourse.julialang.org/t/why-do-we-need-the-do-keyword/22236/2 "2019-03-23T09:13:09Z")

</div>

I don’t know if this is the reason, but I often use it for very complex lambdas. For example, the `by()` function for dataframes:

```julia
by(my_df, :col) do df
    # a whole mess of stuff...
end

```

I’m not sure how easy your macro would be with a multiline expression, but it also doesn’t seem all that much simpler in the example you provided (in that case I’d probably just stick the lambda inside the function call).

---

<div class="post-metadata">

**Author:** ![sagartewari01](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/sagartewari01/32/7810_2.png) [@sagartewari01](https://discourse.julialang.org/u/sagartewari01)\
**Post date:** [March 23, 2019, 10:44am UTC](https://discourse.julialang.org/t/why-do-we-need-the-do-keyword/22236/3 "2019-03-23T10:44:16Z")

</div>

You can use `begin` blocks for complex lambdas, they’re apparently just syntactic sugar for anonymous functions. Here’s a macro which does exactly what `do` keyword does:

```julia
macro m_do(func, callable)
    if !isa(func, Expr) || func.head != :call
        error()
    end
    insert!(func.args, 2, callable)
    return func
end

@m_do map([1,2,3]) x -> begin
    println(x)
    return x*x
end

```

It isn’t very complicated because the parser translates the map call and the lambda to two bulk `sexprs` (I’m not familiar with the source, but it certainly appears so).

---

<div class="post-metadata">

**Author:** ![oxinabox](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/oxinabox/32/206603_2.png) [@oxinabox](https://discourse.julialang.org/u/oxinabox)\
**Post date:** [March 23, 2019, 12:08pm UTC](https://discourse.julialang.org/t/why-do-we-need-the-do-keyword/22236/4 "2019-03-23T12:08:53Z")

</div>

We don’t _need_ it, we want it.

```julia
@do f(y) x -> begin
...
end

```

is longer and less pretty than

```julia
f(y) do x
...
end

```

This is an operation we want to be pretty because it is really commonly used.  
It basically takes the place of python’s `with` statements and more.  
Basically this is a really common and useful pattern.  
Some examples of the places I tend to use it:

```julia
open("file.txt") do fh
...
end

pmap(1:100) do x
...
end

mapreduce(hcat, 1:100) do x
 # return a vector
end

lock(lk) do
...
end

withenv(API_KEY="123423") do 
...
end

mktempdir() do dirname
...
end

sum(xs) do 
    ...
end

```

I wouldn’t like to make all those uglier.

At the end of the day, why do we do anything?  
Since julia is just going to compile to machine code anyway.

Or less reductio ad absurdum: why allow anon functions?  
Why not just have people write functions normally?  
Or use a macro to create real functions out of lambdas syntax?

Looking at the history `do` blocks have been in the language since before [0.1 release](https://github.com/JuliaLang/julia/blob/v0.1/src/julia-parser.scm#L1025-L1032).  
Which is before my time.  
The original reason is thus probably buried in a email chain somewhere.

---

<div class="post-metadata">

**Author:** ![sagartewari01](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/sagartewari01/32/7810_2.png) [@sagartewari01](https://discourse.julialang.org/u/sagartewari01)\
**Post date:** [March 23, 2019, 12:59pm UTC](https://discourse.julialang.org/t/why-do-we-need-the-do-keyword/22236/5 "2019-03-23T12:59:53Z")

</div>

So it’s an ergonomic feature. I didn’t know about these use cases since I’m new to julia. Thanks for clarification.

---

<div class="post-metadata">

**Author:** ![oxinabox](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/oxinabox/32/206603_2.png) [@oxinabox](https://discourse.julialang.org/u/oxinabox)\
**Post date:** [March 23, 2019, 2:06pm UTC](https://discourse.julialang.org/t/why-do-we-need-the-do-keyword/22236/6 "2019-03-23T14:06:54Z")

</div>

> So it’s an ergonomic feature.

Correct.

> I didn’t know about these use cases since I’m new to julia. Thanks for clarification.

You’re welcome

---

<div class="post-metadata">

**Author:** ![StefanKarpinski](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/stefankarpinski/32/24_2.png) [@StefanKarpinski](https://discourse.julialang.org/u/StefanKarpinski)\
**Post date:** [March 23, 2019, 2:53pm UTC](https://discourse.julialang.org/t/why-do-we-need-the-do-keyword/22236/7 "2019-03-23T14:53:47Z")

</div>

> <https://github.com/JuliaLang/julia/issues/441>
>
> This has come up a couple of times. I'd like to accumulate syntax suggestions he…re.

---

<div class="post-metadata">

**Author:** ![longemen3000](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/longemen3000/32/7298_2.png) [@longemen3000](https://discourse.julialang.org/u/longemen3000)\
**Post date:** [March 24, 2019, 1:44am UTC](https://discourse.julialang.org/t/why-do-we-need-the-do-keyword/22236/8 "2019-03-24T01:44:21Z")

</div>

> [@oxinabox](#):
>
> We don’t _need_ it, we want it.

😂😂, best phrase!

---

<div class="post-metadata">

**Author:** ![bramtayl](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/bramtayl/32/3614_2.png) [@bramtayl](https://discourse.julialang.org/u/bramtayl)\
**Post date:** [March 25, 2019, 2:34am UTC](https://discourse.julialang.org/t/why-do-we-need-the-do-keyword/22236/9 "2019-03-25T02:34:32Z")

</div>

I never use do blocks because of [#15276](https://github.com/JuliaLang/julia/issues/15276). There’s no way to combine the `let` block trick with `do` syntax.

---

<div class="post-metadata">

**Author:** ![DNF](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/dnf/32/10191_2.png) [@DNF](https://discourse.julialang.org/u/DNF)\
**Post date:** [March 25, 2019, 8:10am UTC](https://discourse.julialang.org/t/why-do-we-need-the-do-keyword/22236/10 "2019-03-25T08:10:26Z")

</div>

I don’t use `do` blocks, because I can never quite grok them, or at least only for a few hours at a time. I read the documentation, and then _sort of_ get it, but next time around I have no idea.

I think it might be related to the spelling. “Who is `do`ing what to whom?” I can never read it correctly. Sometimes I try to replace it with Python’s “with … as …” and then it’s ok, but most of the time that doesn’t work. In summary, it might not be the concept that’s so hard, but the word `do` really throws me off.

Does anyone have a tip for how to make it sound right inside my head?

---

<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:** [March 25, 2019, 8:22am UTC](https://discourse.julialang.org/t/why-do-we-need-the-do-keyword/22236/11 "2019-03-25T08:22:01Z")

</div>

> [@DNF](#):
>
> Does anyone have a tip for how to make it sound right inside my head?

I am not sure I understand the requirement, but I would not invest too much in mapping it to a construct/sentence in a natural language, and would recommend trying to understand them as they are.

There is not much to `do` blocks, just syntactic sugar.

```julia
f((x, y) -> body..., args...)

```

is equivalent to/can be written as

```julia
f(args...) do x, y
    body...
end

```

---

<div class="post-metadata">

**Author:** ![DNF](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/dnf/32/10191_2.png) [@DNF](https://discourse.julialang.org/u/DNF)\
**Post date:** [March 25, 2019, 8:32am UTC](https://discourse.julialang.org/t/why-do-we-need-the-do-keyword/22236/12 "2019-03-25T08:32:56Z")

</div>

> [@Tamas\_Papp](#):
>
> I would not invest too much in mapping it to a construct/sentence in a natural language, and would recommend trying to understand them as they are.

The reason I try to do that is that even when I occasionally figure out what it means, it never sticks, but seems to slip through my mental fingers, as it were. I don’t have this problem with other parts of the syntax. The substitution/reshuffling of the sequence of ‘things’, as well as the word `do` itself trips me up. I can’t help reading it as “do x, y” (how can I do ‘x, y’?)

Anyway, thanks for the explanation. Maybe there is no ‘trick’.

---

<div class="post-metadata">

**Author:** ![pfitzseb](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/pfitzseb/32/45566_2.png) [@pfitzseb](https://discourse.julialang.org/u/pfitzseb)\
**Post date:** [March 25, 2019, 8:34am UTC](https://discourse.julialang.org/t/why-do-we-need-the-do-keyword/22236/13 "2019-03-25T08:34:40Z")

</div>

I guess the closest you could get is to read

```julia
f(args...) do inner_args...
  ...
end

```

as

```julia
f(args...) does with inner_args...
   these operations
end

```

which makes sense in many cases:

```julia
map(rand(10)) does with x
  x*2
end

```

Or maybe `does to x`?

---

<div class="post-metadata">

**Author:** ![DNF](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/dnf/32/10191_2.png) [@DNF](https://discourse.julialang.org/u/DNF)\
**Post date:** [March 25, 2019, 9:25am UTC](https://discourse.julialang.org/t/why-do-we-need-the-do-keyword/22236/14 "2019-03-25T09:25:34Z")

</div>

Thanks. Maybe a sort of visual substitution is the way to go.
