I have an IDictionary<TKey,TValue>
implementation that internally holds n other Dictionary<TKey, TValue>
and distributes that insertions by the HashCode of the key to the invidual sub-dictionaries. With 16 sub-dictionaries, the number of collisions is pretty low on a 4-core machine.
For parallel insertions, i locked the Add-method with a ReaderWriterLockSlim
, locking only the individual sub-dictionary:
public void Add(TKey key, TValue value)
{
int poolIndex = GetPoolIndex(key);
this.locks[poolIndex].EnterWriteLock();
try
{
this.pools[poolIndex].Add(key, value);
}
finally
{
this.locks[poolIndex].ExitWriteLock();
}
}
When inserting items with four threads, i only got about 32% cpu usage and bad performance. So i replaced the ReaderWriterLockSlim by a Monitor (i.e., the lock
keyword).
CPU usage was now at nearly 100% and the performance was more than doubled.
My question is: Why did the CPU usage increase? The number of collisions should not have changed. What makes ReaderWriterLock.EnterWriteLock wait so many times?
See Question&Answers more detail:
os 与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…