Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Call parallel coroutines and wait for all of them to be over

I have some coroutines:

IEnumerator a(){ /* code */ }
IEnumerator b(){ /* code */ }
IEnumerator c(){ /* code */ }

I want to create a coroutine that calls a, b and c in parallel but wait for all of them to finish before going on, something like:

IEnumerator d(){
    StartCoroutine(a());
    StartCoroutine(b());
    StartCoroutine(c());
    wait until all of them are over
    print("all over");
}

Obviously I could use a boolean for each coroutine to save its current state, but since this approach is not scalable, I'd prefer a more straight-forward solution.

like image 430
Daniel Avatar asked Dec 15 '19 22:12

Daniel


2 Answers

The method that I use, which is also a bit clear code and easy to use:

IEnumerator First() { yield return new WaitForSeconds(1f); }
IEnumerator Second() { yield return new WaitForSeconds(2f); }
IEnumerator Third() { yield return new WaitForSeconds(3f); }

IEnumerator d()
{
    Coroutine a = StartCoroutine(First());
    Coroutine b = StartCoroutine(Second());
    Coroutine c = StartCoroutine(Third());

    //wait until all of them are over
    yield return a;
    yield return b;
    yield return c;

    print("all over");
}
like image 177
Biswadeep Sarkar Avatar answered Sep 30 '22 02:09

Biswadeep Sarkar


You can also use the underlying iterator behind the coroutine and call MoveNext yourself

In your example it will be something like

IEnumerator a(){ /* code */ }
IEnumerator b(){ /* code */ }
IEnumerator c(){ /* code */ }

IEnumerator d(){
    IEnumerator iea = a();
    IEnumerator ieb = b();
    IEnumerator iec = c();
    // Note the single | operator is intended here
    while (iea.MoveNext() | ieb.MoveNext() | iec.MoveNext()) {
        yield return null;
    }
    print("all over");
}

See the documentation about the | operator here https://docs.microsoft.com/en-us/dotnet/csharp/language-reference/operators/boolean-logical-operators#logical-or-operator-
It is basically an || operator but that will evaluate all your expressions thus effectively advancing each iterator even if another is already done.

like image 30
jrmgx Avatar answered Sep 30 '22 02:09

jrmgx