繁体   English   中英

为什么.NET内部Hashtable中有Thread.Sleep(1)?

[英]Why there is a Thread.Sleep(1) in .NET internal Hashtable?

最近,我正在阅读.NET Hashtable的实现,遇到了我不理解的代码。 部分代码是:

int num3 = 0;
int num4;
do
{
   num4 = this.version;
   bucket = bucketArray[index];
   if (++num3 % 8 == 0)
     Thread.Sleep(1);
}
while (this.isWriterInProgress || num4 != this.version);

整个代码在System.Collections.Hashtable (mscorlib Version = 4.0.0.0)的public virtual object this[object key]中。

问题是:

在那里拥有Thread.Sleep(1)的原因是什么?

Sleep(1)是Windows中记录的一种方式,用于产生处理器并允许其他线程运行。 您可以在带有注释的参考源中找到以下代码:

   // Our memory model guarantee if we pick up the change in bucket from another processor,
   // we will see the 'isWriterProgress' flag to be true or 'version' is changed in the reader.
   //
   int spinCount = 0;
   do {
       // this is violate read, following memory accesses can not be moved ahead of it.
       currentversion = version;
       b = lbuckets[bucketNumber];

       // The contention between reader and writer shouldn't happen frequently.
       // But just in case this will burn CPU, yield the control of CPU if we spinned a few times.
       // 8 is just a random number I pick.
       if( (++spinCount) % 8 == 0 ) {
           Thread.Sleep(1);   // 1 means we are yeilding control to all threads, including low-priority ones.
       }
   } while ( isWriterInProgress || (currentversion != version) );

isWriterInProgress变量是易失性布尔。 作者在英语上遇到了一些麻烦,“违禁阅读”是“易失性阅读”。 基本思想是尽量避免屈服,线程上下文切换非常昂贵,并且希望编写者能尽快完成。 如果没有成功,则显式屈服以避免燃烧cpu。 这本来可以用Spinlock编写的,但是Hashtable的年代很长。 关于内存模型的假设也是如此。

在无法访问其余实施代码的情况下,我只能根据您发布的内容进行有根据的猜测。

就是说,它似乎正在尝试更新Hashtable中的某些内容(无论是内存还是磁盘),并在等待它完成之前进行无限循环(通过检查isWriterInProgress可以看出)。

如果是单核处理器,则一次只能运行一个线程。 像这样连续循环很容易意味着另一个线程没有运行的机会,但是Thread.Sleep(1)使处理器有机会给编写者一些时间。 没有等待,编写器线程可能永远不会有运行的机会,也永远不会完成。

我还没有阅读源代码,但看起来像是无锁的并发性事情。 您正在尝试从哈希表中读取数据,但是可能有人正在对其进行写操作,因此您要等到isWriterInProgress设置并且所读取的版本没有更改。

这不能解释为什么我们例如总是至少等待一次。 编辑:那是因为我们没有,感谢@Maciej指出这一点。 如果没有争执,我们将立即进行。 我不知道为什么8是幻数而不是例如4或16。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM