首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >告诉是否不循环地更新并发队列

告诉是否不循环地更新并发队列
EN

Stack Overflow用户
提问于 2015-08-07 19:21:04
回答 3查看 1.3K关注 0票数 0

谢谢你的帮助。我有一个由并发队列链接的三线程进程。线程一处理信息,返回到第二个线程,该线程将数据放入并发队列。第三个线程是这样循环的:

代码语言:javascript
复制
while (true) {
    if(queue.TryDequeue(out info)) {
        doStuff(info);
    } else {
        Thread.Sleep(1);
    }
}

是否有更好的方法来处理它,这样我就不会重复那么多循环了吗?应用程序对性能非常敏感,目前只有TryDequeue占用应用程序运行时的8-9%。希望尽可能减少,但不太确定我的选择是什么。

EN

回答 3

Stack Overflow用户

回答已采纳

发布于 2015-08-07 19:37:57

您应该考虑使用System.Collections.Concurrent.BlockingCollection及其Add() / its ()方法。使用new ()时,您的第三个线程将在等待新项时挂起。Add()是线程安全的,可以由第二个线程使用。

使用这种方法,您应该能够将代码简化为如下内容:

代码语言:javascript
复制
while (true) {
   var info = collection.Take();
   doStuff(info);
}
票数 2
EN

Stack Overflow用户

发布于 2015-08-07 19:36:18

你可以增加睡眠时间。我也会用await Task.Delay代替睡眠。这样,您可以在没有Thread.Sleep使用的额外cpu周期的情况下等待更长时间,并且仍然能够通过使用CancellationTokenSource来取消延迟。

另一方面,有更好的方法来排队等待工作。考虑到您似乎想要同步运行这些作业,例如有一个单例类,它接收工作项并对它们进行排队。因此,如果在添加队列时队列中没有项,则应该检测到该项,然后启动作业处理。在作业过程的末尾,检查是否有更多的工作,使用递归完成该工作,或者如果没有其他作业,则退出作业流程,当您向空队列添加项时,作业流程将再次运行。如果我的假设是错误的,并且您可以并行运行这些作业,那么为什么要使用队列呢?

您可能希望使用ObservableCollection的线程安全实现。看看这个问题ObservableCollection and threading

票数 0
EN

Stack Overflow用户

发布于 2015-08-07 19:41:31

我没有避免循环的推荐,但是我建议你远离

代码语言:javascript
复制
while (true)

然后考虑一下这一点:

代码语言:javascript
复制
MyThing thing;
while (queue.TryDequeue(out thing))
{
    doWork(thing);
}

将其放入每次修改队列时都会调用的方法中,这将确保它在需要时运行,但在不需要时结束。

票数 -1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/31885161

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档