# Finishing a task

**URL:** https://discourse.julialang.org/t/finishing-a-task/86784
**Category:** General Usage
**Tags:** task
**Created:** [September 5, 2022, 7:59am UTC](https://discourse.julialang.org/t/finishing-a-task/86784 "2022-09-05T07:59:18Z")
**Posts on this page:** 6
**Page:** 1

<div class="post-metadata">

### Author: ![cstjean](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/cstjean/32/1444_2.png) [@cstjean](https://discourse.julialang.org/u/cstjean)
#### Post date: [September 5, 2022, 7:59am UTC](https://discourse.julialang.org/t/finishing-a-task/86784/1 "2022-09-05T07:59:18Z")

</div>

If I’m manipulating tasks with `yieldto`, without the scheduler, when a task finishes it just hangs the REPL (i.e. `yieldto(@task 1+1)` hangs). So I have to `yieldto` back to the main task at the end (or is there some other way, without using the scheduler?)

```julia
julia> main = current_task();

julia> t = Task() do
           x = 1 + 1
           yieldto(main, x)
       end
Task (runnable) @0x000000012c776380

julia> yieldto(t)
2

```

but then the task is still “runnable”, it will hang if it’s yielded to again, and its stack is still allocated (at least, until it’s GC’ed). Is there any way to finish the task? I can manually do `t._state = 1`, to make it `done`, then if yielded to it will merely return nothing instead of hanging. Is that how it should be done?

---

<div class="post-metadata">

### Author: ![Ashlin\_Harris](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/ashlin_harris/32/210166_2.png) [@Ashlin\_Harris](https://discourse.julialang.org/u/Ashlin_Harris)
#### Post date: [September 5, 2022, 3:40pm UTC](https://discourse.julialang.org/t/finishing-a-task/86784/2 "2022-09-05T15:40:23Z")

</div>

~~The issue is that the REPL is waiting for a task that hasn’t started yet. `@task` creates a task but doesn’t run it (you can check with `istaskstarted(t)`). Running `schedule(t)` tells the scheduler to start the task.~~ I think you have the right idea. I assumed the task wasn’t getting started, until I tried the following:

```julia
t=Task() do
  println(istaskstarted(t))
end

# yieldto(t) # prints true and hangs
schedule(t) # prints true and ends

```

`yieldto` is a low-level command, as opposed to `schedule`, so you might need to manually schedule tasks and set states when using it. [The docs](https://docs.julialang.org/en/v1/base/parallel/#Base.yieldto) seem to discourage its use for those reasons.

What sort of problem are you solving? Do your tasks need to share data or communicate with each other?

---

<div class="post-metadata">

### Author: ![cstjean](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/cstjean/32/1444_2.png) [@cstjean](https://discourse.julialang.org/u/cstjean)
#### Post date: [September 5, 2022, 6:54pm UTC](https://discourse.julialang.org/t/finishing-a-task/86784/3 "2022-09-05T18:54:34Z")

</div>

For context, [Simple communication between tasks](https://discourse.julialang.org/t/simple-communication-between-tasks/86480)

> What sort of problem are you solving? Do your tasks need to share data or communicate with each other?

Yeah, my problem isn’t “task is waiting on IO so let’s use that time productively”, but rather “coroutines/continuations are cool for decoupling program logic in an AI context”. I don’t think the scheduler is the right tool. `yieldto` is nice, but it feels like the low-level layer is missing a handful of primitives. Indeed, looking at the scheduler code, it is not “implemented in terms of yieldto”, as one might hope, but rather full of C calls.

---

<div class="post-metadata">

### Author: ![jameson](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/jameson/32/23_2.png) [@jameson](https://discourse.julialang.org/u/jameson)
#### Post date: [September 9, 2022, 1:43pm UTC](https://discourse.julialang.org/t/finishing-a-task/86784/4 "2022-09-09T13:43:43Z")

</div>

You want `yield(t)`, not `yieldto(t)` if the REPL is supposed to keep running. Or `schedule(t); wait(t)` if it is not supposed to keep running.

---

<div class="post-metadata">

### Author: ![cstjean](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/cstjean/32/1444_2.png) [@cstjean](https://discourse.julialang.org/u/cstjean)
#### Post date: [September 9, 2022, 2:13pm UTC](https://discourse.julialang.org/t/finishing-a-task/86784/5 "2022-09-09T14:13:17Z")

</div>

Thank you for the answer. I’m a beginner with tasks!

For me, this works as expected:

```julia
julia> t_main = current_task()
Task (runnable) @0x00000001106b0010

julia> t1 = @task begin 
       @show yieldto(t2, 10)
       yieldto(t_main)
       end
Task (runnable) @0x000000013951df90

julia> t2 = @task begin 
       @show yieldto(t1, 100)
       end
Task (runnable) @0x000000013951e0e0

julia> yieldto(t1)
yieldto(t2, 10) = 100

```

even though of course, I’m on the hook for exception handling etc.

This doesn’t work:

```julia
julia> t1 = @task begin 
       @show yield(t2, 10)
       end
Task (runnable) @0x0000000139531900

julia> t2 = @task begin 
       @show yield(t1, 100)
       end
Task (runnable) @0x0000000139531a50

julia> yield(t1)
yield(t2, 10) = # ????
julia> 

```

Presumably it switches to the REPL task in the middle of the `@show()` call?

With `wait`, the `yield` value is absent.

```julia
julia> schedule(t1); wait(t1)
yield(t2, 10) = nothing

```

Sending values back and forth is a big part of my use case. I know that I could work around that in various ways (eg. closing over a `Ref`, or using `Condition`s), but at that point, straight `yieldto` looks equally appealing.

---

<div class="post-metadata">

### Author: ![jameson](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/jameson/32/23_2.png) [@jameson](https://discourse.julialang.org/u/jameson)
#### Post date: [September 9, 2022, 2:41pm UTC](https://discourse.julialang.org/t/finishing-a-task/86784/6 "2022-09-09T14:41:13Z")

</div>

you don’t need to switch all of them
