HM 코드 읽기: 프레임 내 예측(一)
10184 단어 H.265
const UChar g_aucIntraModeNumFast_UseMPM[MAX_CU_DEPTH] =
{
3, // 2x2
8, // 4x4
8, // 8x8
3, // 16x16
3, // 32x32
3 // 64x64
};
const UChar g_aucIntraModeNumFast_NotUseMPM[MAX_CU_DEPTH] =
{
3, // 2x2
9, // 4x4
9, // 8x8
4, // 16x16 33
4, // 32x32 33
5 // 64x64 33
};
위의 두 배열에서 알 수 있듯이 RMD 모드의 개수는 PU의 크기와 관련이 있다.PU가 작은 경우(4x4 또는 8x8) RMD 개수는 8입니다.PU가 큰 경우(16x16 또는 32x32 또는 64x64) RMD 개수는 3입니다.RMD를 선택할 때 uiMode는 대가에 따라 uiCost가CandCostList에서 작게부터 크게CandModeList에 배열됩니다.
UInt TEncSearch::xUpdateCandList( UInt uiMode, Double uiCost, UInt uiFastCandNum, UInt * CandModeList, Double * CandCostList )
{
UInt i;
UInt shift=0;
// shift( )
while ( shift1-shift ] )
{
shift++;
}
if( shift!=0 )
{
//
for(i=1; i<shift; i++)
{
CandModeList[ uiFastCandNum-i ] = CandModeList[ uiFastCandNum-1-i ];
CandCostList[ uiFastCandNum-i ] = CandCostList[ uiFastCandNum-1-i ];
}
//
CandModeList[ uiFastCandNum-shift ] = uiMode;
CandCostList[ uiFastCandNum-shift ] = uiCost;
return 1;
}
return 0;
}
위 함수의 반환 값은TEncSearch::estIntrapredLumaQT에 정의된 변수인 CandNum의 증량으로 사용되지만,CandNum의 값은 사용되지 않기 때문에 위 함수의 반환 값은 쓸모가 없습니다.CandCostList는 작은 순서에서 큰 순서로 뒤로 옮길 때 가장 큰 코스트의 패턴을 덮어쓰는 것이 합리적이다.
RMO 이후 MPM(most probable mode) 모드를 추가합니다.MPM 모드가 RMO에서 생성된 컬렉션에 없으면 MPM 모드를 추가합니다.
if (m_pcEncCfg->getFastUDIUseMPMEnabled())
{
Int uiPreds[NUM_MOST_PROBABLE_MODES] = {-1, -1, -1};
Int iMode = -1;
pcCU->getIntraDirPredictor( uiPartOffset, uiPreds, COMPONENT_Y, &iMode ); // MPM
// MPM
const Int numCand = ( iMode >= 0 ) ? iMode : Int(NUM_MOST_PROBABLE_MODES);
for( Int j=0; j < numCand; j++)
{
Bool mostProbableModeIncluded = false;
Int mostProbableMode = uiPreds[j];
for( Int i=0; i < numModesForFullRD; i++)
{
mostProbableModeIncluded |= (mostProbableMode == uiRdModeList[i]);
}
if (!mostProbableModeIncluded)
{
uiRdModeList[numModesForFullRD++] = mostProbableMode;
}
}
}
MPM 모드의 코드는 다음과 같습니다(포인터 piMode가 가리키는 변수에 MPM의 개수를 붙임).
/** Get most probable intra modes
*\param uiAbsPartIdx partition index
*\param uiIntraDirPred pointer to the array for MPM storage
*\param compID colour component ID
*\param piMode it is set with MPM mode in case both MPM are equal. It is used to restrict RD search at encode side.
*\returns Number of MPM
*/
Void TComDataCU::getIntraDirPredictor( UInt uiAbsPartIdx, Int uiIntraDirPred[NUM_MOST_PROBABLE_MODES], const ComponentID compID, Int* piMode ) const
{
UInt LeftPartIdx = MAX_UINT;
UInt AbovePartIdx = MAX_UINT;
Int iLeftIntraDir, iAboveIntraDir;
const TComSPS *sps=getSlice()->getSPS();
const UInt partsPerMinCU = 1<2*(sps->getMaxTotalCUDepth() - sps->getLog2DiffMaxMinCodingBlockSize()));
const ChannelType chType = toChannelType(compID);
const ChromaFormat chForm = getPic()->getChromaFormat();
// Get intra direction of left PU
const TComDataCU *pcCULeft = getPULeft( LeftPartIdx, m_absZIdxInCtu + uiAbsPartIdx );
if (isChroma(compID))
{
LeftPartIdx = getChromasCorrespondingPULumaIdx(LeftPartIdx, chForm, partsPerMinCU);
}
// PU Intra , DC :Any unavailable prediction mode is considered to be Intra_DC.
iLeftIntraDir = pcCULeft ? ( pcCULeft->isIntra( LeftPartIdx ) ? pcCULeft->getIntraDir( chType, LeftPartIdx ) : DC_IDX ) : DC_IDX;
// Get intra direction of above PU
const TComDataCU *pcCUAbove = getPUAbove( AbovePartIdx, m_absZIdxInCtu + uiAbsPartIdx, true, true );
if (isChroma(compID))
{
AbovePartIdx = getChromasCorrespondingPULumaIdx(AbovePartIdx, chForm, partsPerMinCU);
}
// PU Intra , DC :Any unavailable prediction mode is considered to be Intra_DC.
iAboveIntraDir = pcCUAbove ? ( pcCUAbove->isIntra( AbovePartIdx ) ? pcCUAbove->getIntraDir( chType, AbovePartIdx ) : DC_IDX ) : DC_IDX;
if (isChroma(chType))
{
if (iLeftIntraDir == DM_CHROMA_IDX)
{
iLeftIntraDir = pcCULeft-> getIntraDir( CHANNEL_TYPE_LUMA, LeftPartIdx );
}
if (iAboveIntraDir == DM_CHROMA_IDX)
{
iAboveIntraDir = pcCUAbove->getIntraDir( CHANNEL_TYPE_LUMA, AbovePartIdx );
}
}
assert (2if(iLeftIntraDir == iAboveIntraDir) // PU ,MPM 1。
{
if( piMode )
{
*piMode = 1;
}
if (iLeftIntraDir > 1) // angular modes
{
uiIntraDirPred[0] = iLeftIntraDir;
uiIntraDirPred[1] = ((iLeftIntraDir + 29) % 32) + 2;
uiIntraDirPred[2] = ((iLeftIntraDir - 1 ) % 32) + 2;
}
else //non-angular
{
uiIntraDirPred[0] = PLANAR_IDX;
uiIntraDirPred[1] = DC_IDX;
uiIntraDirPred[2] = VER_IDX;
}
}
else // PU ,MPM 2。
{
if( piMode )
{
*piMode = 2;
}
uiIntraDirPred[0] = iLeftIntraDir; // PU MPM
uiIntraDirPred[1] = iAboveIntraDir; // PU MPM
if (iLeftIntraDir && iAboveIntraDir ) //both modes are non-planar
{
uiIntraDirPred[2] = PLANAR_IDX;
}
else
{
uiIntraDirPred[2] = (iLeftIntraDir+iAboveIntraDir)<2? VER_IDX : DC_IDX;
}
}
for (UInt i=0; iassert(uiIntraDirPred[i] < 35);
}
}
위 코드의 조건if(ischroma(chType)는 모두 만족하지 않으며, 호출할 때 주는chType은 모두COMPONENTY.
이 내용에 흥미가 있습니까?
현재 기사가 여러분의 문제를 해결하지 못하는 경우 AI 엔진은 머신러닝 분석(스마트 모델이 방금 만들어져 부정확한 경우가 있을 수 있음)을 통해 가장 유사한 기사를 추천합니다:
HM 코드 읽기: 프레임 내 예측(一)본고의 코드는 모두 TEncSearch::estIntrapredLumaQT 함수 또는 호출된 함수 중의 코드입니다.TEncSearch::estIntrapredLumaQT 함수에서 RMD(Rough Mode Decis...
텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
CC BY-SA 2.5, CC BY-SA 3.0 및 CC BY-SA 4.0에 따라 라이센스가 부여됩니다.