我在C#中有一个应用程序,它以影片剪辑的形式生成一系列图像,其中包含两种方法。每种方法都会生成一系列图像(每秒帧数),这些图像将显示到我的输出(相应的PictureBox_1和PictureBox_2)。
我的问题是如何将这两个方法中的这些系列图像相互混合,而不是单独播放每个线程我运行第三个线程,即随机混合另外两个线程?
例如输出如下:
线程一:bmp1,bmp1,bmp1,...
线程二:bmp2,bmp2,bmp2,...
线程三; bmp1,bmp1,bmp2,bmp1,bmp2,bmp2,bmp2,bmp1,...
答案 0 :(得分:4)
显而易见的解决方案是将生成的图像从两个线程推送到中央队列,由第三个线程读取。
要通知第三个主题有关新推送图像的信息,您可以使用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);
}
}
}
}
前两个线程产生数字,一个线程在2000-3000之间的范围为1-1000。第三个线程读取生成的结果。
当然而不是int
,你会使用你的Image类。
请注意,上述代码neverEndingConsumer.Wait();
仅用于测试目的。您不希望在代码中使用它,因为它会永久阻止。
另一个提示:如果您从使用者线程访问图片框,请不要忘记使用Invoke来封送对GUI线程的UI访问。
答案 1 :(得分:1)
您可以使用ThreadPool WorkerThread生成yout图像。您在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);
}