⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 fixedqpencoder.cpp

📁 JVT-Z203_jsvm.rar
💻 CPP
📖 第 1 页 / 共 2 页
字号:
//   encode layer until rate is reached and return file size
//
//////////////////////////////////////////////////////////////////////////
void
encode_layer( EncoderParameters& rcEncoderParameters )
{
  //----- initialize -----
  char              acTempString[2048];
  unsigned int      uiLayer          = rcEncoderParameters.uiNumberOfLayers - 1;
  LayerParameters&  rcLayer          = rcEncoderParameters.acLayerParameters[uiLayer];
  double            dSeqLength       = (double)rcEncoderParameters.uiNumberOfFrames / rcEncoderParameters.dFramesPerSecond;
	double            dTarget          = 0.0;
	switch( rcEncoderParameters.uiMode )
	{
	case 0:
		dTarget = 1000.0 / 8.0 * rcLayer.dTarget * dSeqLength;
		break;
	case 1:
		dTarget =                rcLayer.dTarget * 10000.0;
		break;
	default:
		break;
	}
	unsigned int      uiMinTarget = (unsigned int)(int)ceil ( (100.0 - rcLayer.dMinMismatch) / 100.0 * dTarget );
  unsigned int      uiMaxTarget = (unsigned int)(int)floor( (100.0 + rcLayer.dMaxMismatch) / 100.0 * dTarget );
  unsigned int      uiTarget    = ( uiMinTarget + uiMaxTarget + 1 ) / 2;
	unsigned int      uiCurr      = 0;
	unsigned int      uiPrev      = 0;
  unsigned int      uiMin       = 0;
  unsigned int      uiMax       = (unsigned int)-1;
  double            dMinQP      =  1000;
  double            dMaxQP      = -1000;
  int               iMinQP      =  1000;
  int               iMaxQP      = -1000;
  double            dCurrQP          = rcLayer.dStartBaseQpResidual;

  //----- run until rate or psnr matches -----
  rcLayer.uiNumIter = 0;
  rcLayer.dBaseQpResidual = rcLayer.dStartBaseQpResidual;
  rcLayer.dQpModeDecision = rcLayer.dStartQpModeDecision;
  while( true )
  {
    //----- set parameters -----
    const int iCurrQP       = (int)floor( dCurrQP + 0.5 );
    rcLayer.dBaseQpResidual = dCurrQP;
    if( (rcLayer.dStartBaseQpResidual == rcLayer.dStartQpModeDecision) && (rcLayer.uiNumIter < 5) )
    {
      // update QpModeDecision
      rcLayer.dQpModeDecision = rcLayer.dBaseQpResidual;
    }

    printf( "\n##################################" );
    printf( "\n### Layer %u - iteration %u      ###", uiLayer, ++rcLayer.uiNumIter );
    printf( "\n### BaseQpResidual = %lf ###", rcLayer.dBaseQpResidual );
    printf( "\n### QpModeDecision = %lf ###", rcLayer.dQpModeDecision );
    printf( "\n##################################\n" );

		sprintf( acTempString, "%s/%s_layer%d.mot", rcEncoderParameters.cMotionFolder.c_str(), rcEncoderParameters.cLabel.c_str(), uiLayer );
    rcLayer.cMotionFile         = acTempString;
    rcLayer.uiMotionFileMode = 2;

		if( rcEncoderParameters.uiNumberOfIterations > 1 || uiLayer == rcEncoderParameters.uiNumberOfCodedLayers-1 )
		{
    //--- run ---
    encode( rcEncoderParameters );

      //----- get rate -----
      get_rate( rcEncoderParameters, uiLayer );
      //----- get PSNR -----
      get_psnr( rcEncoderParameters, uiLayer );

			sprintf( acTempString, "L%d:   QP = %lf    MQP = %lf    RATE =%10.4lf PSNR =%10.4lf [ %6.3lf %% ] (iteration %u)\n",
				uiLayer,
				rcLayer.dBaseQpResidual,
				rcLayer.dQpModeDecision,
				rcLayer.dRate,
				rcLayer.dPSNR,
				( ((rcEncoderParameters.uiMode == 0)?rcLayer.uiCurrSize:rcLayer.uiCurrPSNR) - dTarget ) / dTarget * 100.0,
				rcLayer.uiNumIter );

		fprintf( stdout, acTempString );
		fprintf( stderr, acTempString );

		uiCurr = (rcEncoderParameters.uiMode == 0) ? rcLayer.uiCurrSize : rcLayer.uiCurrPSNR;
		}
		else
		{
			rcLayer.uiNumIter = 1;
			rcLayer.dRate     = 0;
			rcLayer.dPSNR     = 0;
		}

    //--- check ---
    if( ( uiCurr == uiPrev ) ||
			  ( ( uiCurr >= uiMinTarget && uiCurr <= uiMaxTarget ) || dCurrQP >= MAX_QP || dCurrQP <= MIN_QP || rcLayer.uiNumIter >= rcEncoderParameters.uiNumberOfIterations ) )
    {
      rcLayer.uiMotionFileMode     = ( rcEncoderParameters.uiNumberOfIterations == 1 ) ? 2 : 1;
			rcLayer.dStartBaseQpResidual = rcLayer.dBaseQpResidual;
			rcLayer.dStartQpModeDecision = rcLayer.dQpModeDecision;
      return;
    }

    //--- update intervall borders ---
    if( uiCurr < uiTarget )
    {
      //--- lower border ---
      uiMin  = uiCurr;
      dMinQP = dCurrQP;
      iMinQP = iCurrQP;
    }
    else
    {
      //--- upper border ---
      uiMax  = uiCurr;
      dMaxQP = dCurrQP;
      iMaxQP = iCurrQP;
    }

    //--- get new BaseQpResidual ---
    if( dMinQP != 1000.0 && dMaxQP != -1000.0 )
    {
      //--- two borders ---
      dCurrQP  = dMinQP - dMaxQP;
      dCurrQP *= log( (double)uiMax / (double)uiTarget  );
      dCurrQP /= log( (double)uiMax / (double)uiMin );
      dCurrQP += dMaxQP;
    }
    else if( dMinQP != 1000.0 )
    {
      //--- lower border: decrease BaseQpResidual ---
      double dDQP = dCurrQP - ( dMinQP + DELTA_QP * log( (double)uiMin / (double)uiTarget ) );
      dDQP        = ( dDQP < MIN_DQP ? MIN_DQP : dDQP );
      dCurrQP    -= dDQP;
      if( dCurrQP < MIN_QP )
      {
        dCurrQP   = MIN_QP;
      }
    }
    else
    {
      //--- upper border: increase BaseQpResidual ---
      double dDQP = ( dMaxQP + DELTA_QP * log( (double)uiMax / (double)uiTarget ) ) - dCurrQP;
      dDQP        = ( dDQP < MIN_DQP ? MIN_DQP : dDQP );
      dCurrQP    += dDQP;
      if( dCurrQP > MAX_QP )
      {
        dCurrQP   = MAX_QP;
      }
    }
		uiPrev = uiCurr;
  }
}

#define ROT(x)  {if(x) return 1;}
#define ROF(x)  {if(!x)return 1;}

int
read_line( FILE* pFile, char* pcFormat, void* pPar )
{
  if( pPar )
  {
    int  result = fscanf( pFile, pcFormat, pPar );
    ROF( result );
  }

  for( int n = 0; n < 1024; n++ )
  {
    if( '\n' == fgetc( pFile ) )
    {
      return 0;
    }
  }
  return 1;
}

int
read_config_file( EncoderParameters& cEncoderParameters, FILE* pFile )
{
  char acTempString[1024];
  ROF( pFile );

  ROT( read_line( pFile, "",    NULL ) );
  ROT( read_line( pFile, "",    NULL ) );
  ROT( read_line( pFile, "%s",  acTempString ) );
  cEncoderParameters.cLabel         = acTempString;
  ROT( read_line( pFile, "%s",  acTempString ) );
  cEncoderParameters.cEncoderBinary = acTempString;
  ROT( read_line( pFile, "%s",  acTempString ) );
  cEncoderParameters.cPSNRBinary = acTempString;
  ROT( read_line( pFile, "%s",  acTempString ) );
  cEncoderParameters.cParameterFile = acTempString;
  ROT( read_line( pFile, "%s",  acTempString ) );
  cEncoderParameters.cBitStreamFile = acTempString;
  ROT( read_line( pFile, "%s",  acTempString ) );
  cEncoderParameters.cMotionFolder  = acTempString;
  ROT( read_line( pFile, "%d",  &cEncoderParameters.uiNumberOfFrames ) );
	ROT( read_line( pFile, "%d",  &cEncoderParameters.uiGOPSize ) );
	ROT( read_line( pFile, "%d",  &cEncoderParameters.uiIntraPeriod ) );
  ROT( read_line( pFile, "%lf", &cEncoderParameters.dFramesPerSecond ) );
  ROT( read_line( pFile, "%d",  &cEncoderParameters.uiNumberOfLayers ) );
  ROT( read_line( pFile, "%d",  &cEncoderParameters.uiConstrainedIntraBL ) );
	ROT( read_line( pFile, "%d",  &cEncoderParameters.uiNumberOfIterations ) );
	ROT( read_line( pFile, "%d",  &cEncoderParameters.uiMode ) );
  ROT( read_line( pFile, "",    NULL ) );

  for( unsigned int uiLayer = 0; uiLayer < cEncoderParameters.uiNumberOfLayers; uiLayer++ )
  {
    LayerParameters& rcLayer = cEncoderParameters.acLayerParameters[uiLayer];

    ROT( read_line( pFile, "",    NULL ) );
    ROT( read_line( pFile, "",    NULL ) );
		ROT( read_line( pFile, "%d",  &rcLayer.uiWidth ) );
		ROT( read_line( pFile, "%d",  &rcLayer.uiHeight ) );
		ROT( read_line( pFile, "%s",  acTempString ) );
		rcLayer.cOrgFile = acTempString;
		ROT( read_line( pFile, "%s",  acTempString ) );
		rcLayer.cRecFile = acTempString;
    ROT( read_line( pFile, "%lf", &rcLayer.dTarget ) );
    ROT( read_line( pFile, "%lf", &rcLayer.dMinMismatch ) );
    ROT( read_line( pFile, "%lf", &rcLayer.dMaxMismatch ) );
    ROT( read_line( pFile, "%lf", &rcLayer.dStartBaseQpResidual ) );
    ROT( read_line( pFile, "%lf", &rcLayer.dStartQpModeDecision ) );
		ROT( read_line( pFile, "%d",  &rcLayer.uiEntropyCodingModFlag ) );
		ROT( read_line( pFile, "%d",  &rcLayer.uiInterLayerPredictionMode ) );
		ROT( read_line( pFile, "%d",  &rcLayer.iBaseLayerId ) );
  }

  return 0;
}

int main( int argc, char** argv)
{
  EncoderParameters cEncoderParameters;
	char              acTempString[2048];
  
	printf( "JSVM SVC FixedQPEncoder \n\n");
  
  USAGE( argc < 2 );
  FILE* pFile = fopen( argv[1], "rt" );
  if( ! pFile )
  {
    printf("\n\nCannot open config file \"%s\"\n\n", argv[1] );
    exit(1);
  }
  else
  {
    if( read_config_file( cEncoderParameters, pFile ) )
    {
      printf("\n\nError while reading from config file \"%s\"\n\n", argv[1] );
      exit(1);
    }
    fclose( pFile );
  }

  //----- iterative encode -----
  cEncoderParameters.uiNumberOfCodedLayers = cEncoderParameters.uiNumberOfLayers;
  for( unsigned int uiNumLayers = 1; uiNumLayers <= cEncoderParameters.uiNumberOfCodedLayers; uiNumLayers++ )
  {
    cEncoderParameters.uiNumberOfLayers = uiNumLayers;
    encode_layer( cEncoderParameters );
  }

  //----- output -----
	fprintf( stdout, "\n\n\n" );
  fprintf( stderr, "\n\n\n" );
  for( unsigned int uiLayer = 0; uiLayer < cEncoderParameters.uiNumberOfLayers; uiLayer++ )
  {
		LayerParameters& rcLayer = cEncoderParameters.acLayerParameters[uiLayer];
    if( cEncoderParameters.uiNumberOfIterations == 1 && uiLayer < cEncoderParameters.uiNumberOfLayers-1 )
  {
      //----- get PSNR -----
      get_psnr( cEncoderParameters, uiLayer );
    }
		sprintf( acTempString, "L%d:   QP = %lf    MQP = %lf    RATE =%10.4lf PSNR =%10.4lf [ %6.3lf %% ] (%u iterations)\n",
      uiLayer,
			rcLayer.dBaseQpResidual,
			rcLayer.dQpModeDecision,
			rcLayer.dRate,
			rcLayer.dPSNR,
			( ((cEncoderParameters.uiMode == 0)?rcLayer.dRate:rcLayer.dPSNR) - rcLayer.dTarget ) / rcLayer.dTarget * 100.0,
			rcLayer.uiNumIter );
		fprintf( stdout, acTempString );
		fprintf( stderr, acTempString );
  }
  printf("\n\n\n");

  return 0;
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -