My understanding is that if you are using a generic list (List) in C#, that it can support multiple concurrent readers but only one writer. And when you introduce a writer into the mix, you must also provide synchronization constructs to make the operations thread safe.
Is List.Contains considered a read operation? In other words, if I am calling this method, do I need to worry that a writer may be writing to this List at the same time?
If you use Reflector to inspect at the code, you get something like this:
public bool Contains(T item)
{
if (item == null)
{
for (int j = 0; j < this._size; j++)
{
if (this._items[j] == null)
{
return true;
}
}
return false;
}
EqualityComparer<T> comparer = EqualityComparer<T>.Default;
for (int i = 0; i < this._size; i++)
{
if (comparer.Equals(this._items[i], item))
{
return true;
}
}
return false;
}
As you can see, it is a simple iteration over the items which is definitely a 'read' operation. If you are using it only for reads (and nothing mutates the items), then no need to lock. If you start modifying the list in a separate thread, then you most decidedly need to synchronize access.
Yes, you should. Basically I would synchronize for any operation if the list might be used for writing at the same time.
Generally I find collections fall into two categories - ones which are created, initialized and then never changed again (thread-safe), and ones which are mutated over time (not thread-safe, lock for all access).
Yes, you do have to worry! List.Contains just gets an EqualityComparer and then loops through all items the list contains comparing the item passed as parameter with the item at the index of the current iteration, so if the list gets modified while being iterated, results may be unpredictable.
List<T>.Contains
is most certainly a read operation. It is possible that some other thread is writing to the collection as you read it.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With