我有许多必须实时处理视频流的模块.简单的方法是使用帧缓冲区,模块从中获取视频图像,处理,然后删除它们.
问题#1:并非所有模块都以相同的速度工作.有些能够处理所有帧,有些则不能.因此,某些模块不会处理所有帧.如果我在删除缓冲区之前等待所有模块完成作业,那么较快的模块将无理由地停止(图A).
一个简单的解决方案将是图B.每个模块的单独缓冲区.如果缓冲区已满,则不会放置帧.但问题#2出现了:内存被浪费:有些帧在不同的缓冲区中会有多个副本.
更智能的解决方案是一个物理缓冲区,附加更多逻辑缓冲区,如图C所示.当至少一个逻辑缓冲区可以容纳它时,在真实缓冲区中添加一个帧,并且当删除链接到它的所有逻辑缓冲区时删除实际缓冲区.(一个简单的实现解决方案由智能指针给出 - 向缓冲区添加一个智能指针到可以容纳它的所有逻辑缓冲区)问题3:在最坏的情况下,可能会发生每个帧被分配给一个模块,而不是共享,它将是解决方案B的一个混乱的缺点.
题
有没有更好的方法来处理这个问题?标准答案?实现它的模板库?
编辑 这种使用缓冲区的机制很复杂,但如果缓冲区已满,则删除帧,在不同平台上提供可扩展的解决方案:无论模块或硬件性能如何,我都会处理尽可能多的帧.

以下是我在生产实时视频系统中看到的两种方法:
与选项 A 类似,存储单个缓冲区列表,但向每个缓冲区添加两组标志。第一组标志指定需要在缓冲区上执行哪些任务,第二组标志指定哪些任务已经执行。当每个模块准备就绪时,它将扫描缓冲区列表,直到找到可以提供帮助的缓冲区。
与选项 C 类似,使用多个包含指向实际帧数据的指针的 fifo。使用引用计数来跟踪哪些帧仍然有效。这意味着每次您创建一个指向帧的新指针时,您都会调用一个函数来增加其引用计数,而每次您完成该指针时,您都会调用一个函数来减少引用计数。一旦帧的引用计数达到零,就可以重新使用帧。
在我看来,第一种方法更容易实现,如果您有少量未完成的帧和少量的处理任务,那么就可以了,但第二种方法更通用,应该更容易扩展到更复杂的系统。
| 归档时间: |
|
| 查看次数: |
351 次 |
| 最近记录: |