如何在HM中添加新的语法元素(HEVC测试模型)

时间:2016-12-08 16:40:00

标签: hevc video-codecs video-compression

我一直在研究HM参考软件,以改进帧内预测部分。现在一个新的帧内预测算法被添加到代码中,我让编码器在我的算法和HM的默认算法之间进行选择(当然根据RDCost)。

我现在需要的是为每个PU发信号,以便解码器能够执行与编码器在速率失真环路中决定的算法相同的算法。

我想知道我应该做些什么来正确地将这一位标志添加到流中,而不会破坏代码中的任何内容。

假设我想使用CABAC上下文模型来跟踪我的旗帜的统计数据,我还应该做些什么:

  1. ContextModel3DBuffer m_cCUIntraAlgorithmSCModel文件添加新的上下文模型,例如TEncSbac.h
  2. 通过查看HM如何初始化其他上下文模型来正确初始化模型(在编码器和解码器端)。
  3. 分别在编码器端和解码器端调用函数m_pcBinIf->encodeBin(myFlag, cCUIntraAlgorithmSCModel)m_pcTDecBinIfdecodeBin(myFlag, cCUIntraAlgorithmSCModel)
  4. 我采取了这三个步骤,但显然它打破了一些东西。

    PS:即使是等概率信令(即不使用CABAC上下文)也是有用的。我只想和平地发送这面旗帜!

    提前致谢。

1 个答案:

答案 0 :(得分:0)

我终于可以解决这个问题了。这是CABAC上下文初始化中的一个错误。

但我想分享这段经历,因为很多人可能想要做同样的事情。

我解释的三个步骤对于添加新的语法元素基本上是必要的,但是可能会对以下内容非常小心:

  1. 首先,您需要决定是否要为语法元素使用单独的上下文模型?或者你想使用现有的?在CABAC分离的情况下,您应该定义ContextModel3DBuffer,并且最好的方法是:在代码中找到类似的语法元素;然后复制它的`ContextModel3DBuffer''定义及其在代码中出现的所有内容。这样可以确保您正在考虑所有事情。
  2. 每个语法元素的编码发生在两个不同的地方:第一,在RDO循环中做出"决定",第二,在实际编码阶段和决策被编码时(例如{ {1}}功能)。
  3. 编码/解码合成元素的顺序在编码器/解码器侧应该相同。例如,如果您的新语法元素在编码器端encodeCtu之后和splitFlag之前编码,则应在解码器端的predModesplitFlag之间准确解码。
  4. 上下文模型是作为一个3D矩阵实现的,以便分别跟踪不同块大小,组件等的合成元素的统计信息。这意味着当你想调用函数predMode时,你可能会确保使用正确的索引。我在这部分犯了愚蠢的错误!
  5. 除了上面的评论之外,我发现函数encodeBin对于调试非常有用。当您有权访问CABAC上下文模型时,此函数会在代码的任意位置返回该状态。当您不匹配时,比较编码器和解码器的相同位置的状态非常有用。例如,您编码getState时会发生很多事情,但您解码1。在这种情况下,您需要在编码和解码之前检查CABAC上下文的状态。它们应该是一样的。如果它们不相同,则追溯错误以找到第一个不匹配的位置。

    我希望它有所帮助。