在调试HM 16.2的解码时,我看到CU看起来像是被细分为PU。每个PU都具有相同的MV。允许CU内的不同MV是我(当前)知道将CU分成PU的唯一原因。
我想知道我是否误解了CTU数据结构(TComDataCU
)*。谁能帮我这个?你知道是否有其他理由将CU拆分为PU?
相关问题:
TComDataCU
将64x64 CTU拆分为256个部分? (我最初预计会看到64个零件,每个最小的8x8 CU都有一个零件。现在我假设附加零件允许更小的PU / TU。)TComMv::getHor()
和TCovMv::getVer()
直接解释为MV是正确的,还是必须合并一些其他信息(例如合并/跳过信息,增量等等)以获得“真实” MV? *对于名为TComDataCU*
的{{1}},我看到了
ctu
和ctu->getTotalNumPart() == 256
ctu->getDepth(48) == 3
ctu->getPredictionMode(48) == INTER_MODE
ctu->getPartitionSize(48) == Nx2N
(仅使用单一预测,使用简单的GOP:I< -P< -P< -P ...),
mvf = ctu->getCUMvField(REF_PIC_LIST_0)
将这些观察结果与我的问题联系起来,对于这个CU,我理解CU有两个包含指数48,50和49,51的PU,如
+--+--+ |48|49| +--+--+ |50|51| +--+--+
所以我希望
mvf->getMv(48).getHor() == mvf->getMv(50).getHor() &&
mvf->getMv(49).getHor() == mvf->getMv(51).getHor() &&
mvf->getMv(48).getVer() == mvf->getMv(50).getVer() &&
mvf->getMv(49).getVer() == mvf->getMv(51).getVer() &&
mvf->getMv(48).getHor() == mvf->getMv(49).getHor() &&
mvf->getMv(48).getVer() == mvf->getMv(49).getVer()
为什么两个PU(看起来)具有相同的MV?
答案 0 :(得分:1)
首先,正如您所注意到的,HEVC中最小的块大小是4x4。 CU只能采用64x64和8x8之间的大小,但PU或TU可以降至4x4。 除了你引用的原因之外,在帧内编码的情况下CU也可以被分成4个PU,并且4个PU可以具有不同的帧内预测方向。
由于最小块大小为4x4,64x64 CTU由256个部分组成。
在HM参考软件中,CTU TComDataCU
的数据结构将始终包含所有可能的最小块,而与实际块结构无关。
这就是为什么(可能是这种情况)CU数据被冗余存储的原因。
例如,名为ctu
的64x64 CTU包含单个CU(因此CU大小为64x64)将存储256个深度0。如果你检查(z-scan)索引0 ctu->getDepth(0)
处的深度,你将得到0.这足以描述CU的大小,但是如果你检查另一个索引的深度{{1} },你也会得到0,这是多余的。
这是你在案件中观察到的。您的CU被分成2个垂直PU(Nx2N),因此(48,50)是单个PU并且用一个运动矢量来描述。但是,HM中的数据结构将MV存储在48和50两个位置。
为了解决你的第二个相关问题,是的,MV的水平和垂直部分“真实地”描述了它。但是,您可能还需要引用帧的索引。这可以在ctu->getDepth(48)
中找到,TComMvField
除此之外还有TComMv
索引。