我有两个线程,一个需要轮询一堆单独的静态资源以查找更新。另一个需要获取数据并将其存储在数据库中。线程 1 如何告诉线程 2 有东西要处理?
skbergam
问问题
1512 次
4 回答
7
如果数据片段是独立的,则将数据片段视为要由线程池处理的工作项。使用线程池并将QueueUserWorkItem
数据发布到线程。您应该使用对称线程池获得更好的可伸缩性,并限制生产者和消费者之间必须发生的同步量。
例如(来自MSDN):
TaskInfo ti = new TaskInfo("This report displays the number {0}.", 42);
// Queue the task and data.
if (ThreadPool.QueueUserWorkItem(new WaitCallback(ThreadProc), ti)) {
Console.WriteLine("Main thread does some work, then sleeps.");
// If you comment out the Sleep, the main thread exits before
// the ThreadPool task has a chance to run. ThreadPool uses
// background threads, which do not keep the application
// running. (This is a simple example of a race condition.)
Thread.Sleep(1000);
Console.WriteLine("Main thread exits.");
}
else {
Console.WriteLine("Unable to queue ThreadPool request.");
}
// The thread procedure performs the independent task, in this case
// formatting and printing a very simple report.
//
static void ThreadProc(Object stateInfo) {
TaskInfo ti = (TaskInfo) stateInfo;
Console.WriteLine(ti.Boilerplate, ti.Value);
}
于 2008-09-20T03:38:43.667 回答
5
我在工作项队列上使用 Monitor.Wait / Pulse。
于 2008-09-20T03:34:13.270 回答
0
“存储在数据库中”线程是否总是需要运行?似乎最好的选择(如果可能的话)是让轮询线程启动另一个线程来进行保存。但是,根据创建的线程数,让第一个轮询线程使用 ThreadPool.QueueUserWorkItem() 可能是更有效的路线。
为了提高效率,当保存到数据库时,我会在数据库上使用异步 I/O 而不是同步方法。
任何时候您都可以不必在两个线程之间直接通信,您应该这样做。必须将一些同步原语放在一起,您的代码不会那么容易调试,并且可能会引入一些非常微妙的竞争条件,这些条件会导致“百万分之一执行”类型的错误(查找/修复远非有趣)。
如果第二个线程总是需要执行,请通过更多信息告诉我们原因,我们可以返回更深入的答案。
祝你好运!
于 2008-09-20T03:48:19.353 回答
0
我个人会让线程 1 引发线程 2 可以响应的事件。线程可以通过启动两个线程的控制进程连接到适当的事件。
于 2008-09-20T06:05:10.973 回答