【问题标题】:Thread Pool of workers in a Window service?Window服务中的工作线程池?
【发布时间】:2013-12-06 17:12:28
【问题描述】:

我正在创建一个包含 2 个独立组件的 Windows 服务: 1 个组件创建作业并将它们插入数据库(1 个线程) 第二个组件处理这些作业(线程池中的多个 FIXED # 线程)

只要服务在运行,这两个组件就会一直运行。

我坚持的是确定如何实现这个线程池。我做了一些研究,似乎有很多方法可以做到这一点,例如创建一个覆盖方法“ThreadPoolCallback”的类,以及使用 ThreadPool.QueueUserWorkItem 对工作项进行排队。 http://msdn.microsoft.com/en-us/library/3dasc8as.aspx

但是在给出的示例中,它似乎不适合我的场景。我想最初在线程池中创建固定数量的线程。然后喂它工作来处理。我该怎么做?

// 用于线程池的包装器方法。

public void ThreadPoolCallback(Object threadContext)
{
    int threadIndex = (int)threadContext;
    Console.WriteLine("thread {0} started...", threadIndex);
    _fibOfN = Calculate(_n);
    Console.WriteLine("thread {0} result calculated...", threadIndex);
    _doneEvent.Set();
}

Fibonacci[] fibArray = new Fibonacci[FibonacciCalculations];
const int FibonacciCalculations = 10;

for (int i = 0; i < FibonacciCalculations; i++)
{
      ThreadPool.QueueUserWorkItem(f.ThreadPoolCallback, i);
}

【问题讨论】:

    标签: c# multithreading windows-services


    【解决方案1】:

    创建一个BlockingCollection 的工作项。创建作业的线程将它们添加到此集合中。

    创建固定数量的持久线程,从 BlockingCollection 读取项目并处理它们。比如:

    BlockingCollection<WorkItem> WorkItems = new BlockingCollection<WorkItem>();
    
    void WorkerThreadProc()
    {
        foreach (var item in WorkItems.GetConsumingEnumerable())
        {
            // process item
        }
    }
    

    多个工作线程可以同时执行此操作。 BlockingCollection 支持多个读取器和写入器,因此您无需处理并发问题。

    请参阅我的博客文章Simple Multithreading, part 2,了解使用一个消费者和一个生产者的示例。添加多个消费者非常简单,只需为每个消费者创建一个新任务即可。

    另一种方法是使用信号量来控制当前正在处理的作业数量。我在this answer 中展示了如何做到这一点。但是,我认为共享的BlockingCollection 通常是更好的解决方案。

    【讨论】:

    • 嗯,创建作业的线程只是将它们插入数据库。工作线程应该从数据库中读取作业。所以从某种意义上说 BlockingCollection 就是数据库。
    • @HenleyChiu:只要您的工作线程知道何时将新项目添加到数据库中,那么它们就不会不断地轮询数据库以寻找新工作,那就很好了。跨度>
    【解决方案2】:

    .NET 线程池并不是真正为固定数量的线程而设计的。它旨在以最佳方式使用机器的资源来执行多个相对较小的工作。

    也许对您来说更好的解决方案是实例化固定数量的BackgroundWorkers?还有一些reasonable BW examples

    【讨论】:

    • 因此,如果我想要 5 个工人,我会这样做:BackgroundWorker[] workers = new BackgroundWorker[5]; for(int i = 0 ; i
    • 就是这样 - 相对简单。您可能还希望使 BW 可取消,以便它们可以侦听来自主线程的取消指令。
    猜你喜欢
    • 2020-06-12
    • 1970-01-01
    • 2018-01-20
    • 1970-01-01
    • 1970-01-01
    • 2013-11-15
    • 1970-01-01
    • 2014-01-19
    • 2018-05-16
    相关资源
    最近更新 更多