繁体   English   中英

如何在C#中混合两个不同线程的输出?

[英]How can I mix the output of two different threads in C#?

我在C#中有一个应用程序,该应用程序以影片剪辑的形式生成一系列图像,其中包含两种方法。 每种方法都会生成一系列图像(每秒帧数),这些图像将显示在我的输出中(相应地显示为PictureBox_1和PictureBox_2)。

我的问题是如何从两种方法相互随机而不是分别打每个线程我运行第三个线程被随机其他两个线程的混合搭配这这些系列的图像?

例如,输出如下:

线程一:bmp1,bmp1,bmp1,……

线程二:bmp2,bmp2,bmp2,…

线程三; bmp1,bmp1,bmp2,bmp1,bmp2,bmp2,bmp2,bmp1等

显而易见的解决方案是将两个线程生成的图像推送到中央队列,该队列由第三个线程读取。

要向第三线程通知新推送的图像,可以使用AutoResetEvent


好,给你一个简单的例子。

  class Program
  {
    static ConcurrentQueue<int> _centralQueue = new ConcurrentQueue<int>();
    static AutoResetEvent _signaller = new AutoResetEvent(false);

    static void Main(string[] args)
    {
      Task.Factory.StartNew(() => Producer1Thread());
      Task.Factory.StartNew(() => Producer2Thread());

      var neverEndingConsumer = Task.Factory.StartNew(() => ConsumerThread());
      neverEndingConsumer.Wait();
    }

    static void Producer1Thread()
    {
      for (int i=2000; i<3000; i++)
      {
        _centralQueue.Enqueue(i);
        _signaller.Set();          
        Thread.Sleep(8);
      }
    }

    static void Producer2Thread()
    {
      for (int i = 0; i < 1000; i++)
      {
        _centralQueue.Enqueue(i);
        _signaller.Set();
        Thread.Sleep(10);
      }
    }

    static void ConsumerThread()
    {
      while (true)
      {
        if (_centralQueue.IsEmpty)
        {
          _signaller.WaitOne();
        }
        int number;
        if (_centralQueue.TryDequeue(out number))
        {
          Console.WriteLine(number);
        }        
      }
    }
  }

前两个线程产生数字,一个线程范围在1-1000,另一个在2000-3000。 第三线程读取产生的结果。

当然,您可以使用Image类代替int

请注意,上面的代码执行neverEndingConsumer.Wait(); 仅用于测试目的。 您不希望它在代码中永久阻塞。

另一个提示:如果您从使用者线程访问图片框,请不要忘记使用Invoke封送对GUI线程的UI访问。

您可以使用ThreadPool WorkerThread生成图像。 您在ThreadPool-Thread中提供的序列必须与处理的序列不同。

这似乎有点随机...

未经测试或编译,仅是伪代码:

QueueUserWorkItem(()=>
{
    // code that generates the image
    var img = GenerateImage();
    // set image to PictureBox via SynchronizationContext of the UI-Thread
    formSyncContext.Send(()=> pb.Image = img);
}

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM