制片人/消费者 - 层叠方法?

时间:2012-08-24 20:46:22

标签: c# winforms .net-4.0 task-parallel-library producer-consumer

我目前正在使用.net 4.0和winforms构建一个与服务器相关的小型应用程序。我想使用任务并行lib的优点,但我对这里的最佳或“正确”实现有点动摇。

目的:

  1. 使用正则表达式模式从网络路径中消耗文件(每15分钟消耗一次。)
  2. 阅读文件(csv风格)
  3. 重写文件以跳过某些列
  4. 通过批量插入或更新将文件数据传输到sql server
  5. 我正在考虑采用级联方式,如下所示:

    ProducerConsumerTask1(从网络路径获取文件/使文件可供阅读)
    ProducerConsumerTask2(从Task1读取文件/从Task1重写文件)
    ProducerConsumerTask3(获取重写文件/将文件从Task2传输到DB)

    还有一点代码:

    private static BlockingCollection<ManagedFile> searchQueue = new BlockingCollection<ManagedFile>(limit);
    private const int limit = 100;
    
    public void StartFileTask()
    {
        Task[] producers = new Task[1];
        producers[0] = Task.Factory.StartNew(() => ProduceFileSearchTask());
    
    
        Task.Factory.StartNew(() => ConsumeFileSearchTask());
    }
    
    public static void ProduceFileSearchTask()
    {
        var pattern = new Regex(Properties.Settings.Default.DefaultRegexPattern);
        string path = Properties.Settings.Default.DefaultImportPath;
    
        IEnumerable<FileInfo> files = new DirectoryInfo(path)
                                            .EnumerateFiles("*.*", SearchOption.AllDirectories)
                                            .Where(x => pattern.IsMatch(x.Name));
    
        for (int i = 0; i < files.ToList().Count(); i++)
        {
            ManagedFile _managedFile = new ManagedFile();
            _managedFile.Id = Guid.NewGuid();
            _managedFile.ManagedFileName = files.ElementAt(i).FullName;
            _managedFile.ManagedFileAddedOn = DateTime.Now;
    
            if (!searchQueue.IsAddingCompleted)
                searchQueue.Add(_managedFile);
    
            Thread.SpinWait(100000); 
        }           
    }
    
    public static void ConsumeFileSearchTask()
    {
        foreach (var item in searchQueue.GetConsumingEnumerable())
        {
            // use ProducerTask for Reading the Files here
        }
    }
    

    如果有人分享他对这个想法的想法,那就太好了。这是一个很好的处理方式吗?在这种情况下哪些更好?在这种情况下的另一个主题:ui的ui自动化/报告/状态更新怎么样?如何才能做到这一点?活动/代表,嗯?

    谢谢!

1 个答案:

答案 0 :(得分:1)

添加我的评论作为答案:)

这看起来像是使用Tasks.Dataflow的完美场景。看看这个,它可能对你有很大的帮助:Tasks.DataFlow Whitepaper

另一种建议方法: 一个任务读取新文件并将其中一些放入BlockingCollection(又名生产者 - 消费者)。使用者任务维护一个并发任务列表,并从集合中读取以安排新任务。通过调整消费者任务以及它可以同时跟踪的文件数量,您可以检查性能。一旦消费者收到某个任务完成的通知,再次从生产者处读取并安排另一个任务。它们将是独立的并行。

要查看的另一个框架是Reactive Extensions并将您的源转换为可观察的文件集合并在那里应用限制。

相关问题