Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Is yield return reentrant?

Can a static function in a static class which uses yield return to return an IEnumerable safely be called from multiple threads?

public static IEnumerable<FooClass> FooClassObjects()
{
    foreach (FooClassWrapper obj in listOfFooClassWrappers)
    {
        yield return obj.fooClassInst;
    }
}

Will each thread that calls this always receive a reference to each object in the collection? In my situation listOfFooClassWrappers is written to once at the beginning of the program, so I don't need to worry about it changing during a call to this function. I wrote a simple program to test this, and I didn't see any indication of problems, but threading issues can be difficult to suss out and it's possible that the issue simply didn't show up during the runs that I did.

EDIT: Is yield return in C# thread-safe? is similar but addresses the situation where the collection is modified while being iterated over. My concern has more to do with multiple threads each getting only part of the collection due to a hidden shared iterator given that the class and method are both static.

like image 845
event44 Avatar asked Dec 14 '15 15:12

event44


People also ask

Does yield break return null?

"yield break" breaks the Coroutine (it's similar as "return"). "yield return null" means that Unity will wait the next frame to finish the current scope. "yield return new" is similar to "yield return null" but this is used to call another coroutine.

Is yield return thread safe?

As written it is thread safe but if you comment out the lock(_sync) in AllValues you should be able to verify that it is not thread safe by running it a few times.

What does yield return do in C#?

You use a yield return statement to return each element one at a time. The sequence returned from an iterator method can be consumed by using a foreach statement or LINQ query. Each iteration of the foreach loop calls the iterator method.

What is yield break?

It specifies that an iterator has come to an end. You can think of yield break as a return statement which does not return a value. For example, if you define a function as an iterator, the body of the function may look like this: for (int i = 0; i < 5; i++) { yield return i; } Console.


Video Answer


1 Answers

Can a static function in a static class which uses yield return to return an IEnumerable safely be called from multiple threads?

The yield keyword makes the IEnumerable<T> returning method/property an iterator. When materialized, it is invoked and internally IEnumerable.GetEnumerator() is called -- which is thread-safe. This returns a single instance.

Check out this explanation: https://startbigthinksmall.wordpress.com/2008/06/09/behind-the-scenes-of-the-c-yield-keyword/

Additionally, this has been asked in a similar manner here.

like image 117
David Pine Avatar answered Oct 21 '22 18:10

David Pine