SpinWait VS睡眠等。使用哪一个? [英] SpinWait vs Sleep waiting. Which one to use?

查看:1791
本文介绍了SpinWait VS睡眠等。使用哪一个?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

它是有效的。

SpinWait.SpinUntil(() => myPredicate(), 10000)

对于10000ms的超时

for a timeout of 10000ms

是不是更有效地使用 Thread.sleep代码轮询相同的条件下
例如一些大致如下 SleepWait 函数的行:

Is it more efficient to use Thread.Sleep polling for the same condition For example something along the lines of the following SleepWait function:

public bool SleepWait(int timeOut)
{
    Stopwatch stopwatch = new Stopwatch(); 
    stopwatch.Start();
    while (!myPredicate() && stopwatch.ElapsedMilliseconds < timeOut)
    {
       Thread.Sleep(50)
    }  
    return myPredicate()
}

我而言,所有的收益SpinWait的可能不是一个很好的使用模式,如果我们谈论的是在1秒超时?这是一个有效的假设?

I'm concerned that all the yielding of SpinWait may not be a good usage pattern if we are talking about timeouts over 1sec? Is this a valid assumption?

哪种方法你preFER,为什么?是否有其他更好的方法?

Which approach do you prefer and why? Is there another even better approach?

更新 - 成为更具体的:

Update - Becoming more specific:

有没有一种方法,使BlockingCollection脉冲休眠线程,当它达到容量有限?我宁愿避免忙等待产品总数为马克碎石建议。

Is there a way to Make BlockingCollection Pulse a sleeping thread when it reaches bounded capacity? I rather avoid a busy waits alltogether as Marc Gravel suggests.

推荐答案

的办法是有一定的机制,为主动探测的东西变成真正的(而不是被动地投票具有的成为IT 的真);这可能是任何类型的等待句柄,或者一个工作等待,或者一个事件,您可以订阅扯去自己。当然,如果你做那种等到出了事,也就是还是不是有效,因为只要有工作的下位完成的作为回调的,意义:你不需要使用一个线程等待。 工作 ContinueWith 这一点,或者你可以做一个事件的工作时,它被炒鱿鱼。在事件可能是最简单的做法,根据上下文。 工作,但是,已经为你在这里谈论的,包括与超时等待和回调机制最一切。

The best approach is to have some mechanism to actively detect the thing becoming true (rather than passively polling for it having become true); this could be any kind of wait-handle, or maybe a Task with Wait, or maybe an event that you can subscribe to to unstick yourself. Of course, if you do that kind of "wait until something happens", that is still not as efficient as simply having the next bit of work done as a callback, meaning: you don't need to use a thread to wait. Task has ContinueWith for this, or you can just do the work in an event when it gets fired. The event is probably the simplest approach, depending on the context. Task, however, already provides most-everything you are talking about here, including both "wait with timeout" and "callback" mechanisms.

是的,旋转10秒不是很大。如果你想使用类似当前的code,如果你有理由期待一个短暂的延迟,但需要允许更长的 - 也许 SpinWait 的(说)​​为20ms,并使用睡眠的休息吗?

And yes, spinning for 10 seconds is not great. If you want to use something like your current code, and if you have reason to expect a short delay, but need to allow for a longer one - maybe SpinWait for (say) 20ms, and use Sleep for the rest?

重新注释;这里就是我想一个勾是全机制:

Re the comment; here's how I'd hook an "is it full" mechanism:

private readonly object syncLock = new object();
public bool WaitUntilFull(int timeout) {
    if(CollectionIsFull) return true; // I'm assuming we can call this safely
    lock(syncLock) {
        if(CollectionIsFull) return true;
        return Monitor.Wait(syncLock, timeout);
    }
}

用,在放回集code:

with, in the "put back into the collection" code:

if(CollectionIsFull) {
    lock(syncLock) {
        if(CollectionIsFull) { // double-check with the lock
            Monitor.PulseAll(syncLock);
        }
    }
}

这篇关于SpinWait VS睡眠等。使用哪一个?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆