x264 rdo

x264 在编码完成一个宏块后,会重新根据rdo参数再次编码一次。

举个例子,如果最终得到的satd 是 20,当前的量化qp是25,计算出来的结果就全部是0,cbp 的6bits 全是0,x264 rdo 会尝试把qp值调小一点,重新编码一次,以减少细节损失。

对应看下源码:

x264_macroblock_analyse()-->x264_macroblock_encode( h );

在宏块分析里面先是做了一次编码

的最后几行

if( analysis.i_mbrd == 3 && !IS_SKIP(h->mb.i_type) )
        mb_analyse_qp_rd( h, &analysis ); //如果不是skip 宏块,则做rdo

static inline void mb_analyse_qp_rd( x264_t *h, x264_mb_analysis_t *a )// RDO 选择QP
{//根据  RDO来调整 qp的值
    int bcost, cost, failures, prevcost, origcost;
    int orig_qp = h->mb.i_qp, bqp = h->mb.i_qp;
    int last_qp_tried = 0;
    origcost = bcost = rd_cost_mb( h, a->i_lambda2 );// 计算宏块的cost
    int origcbp = h->mb.cbp[h->mb.i_mb_xy];

    /* If CBP is already zero, don't raise the quantizer any higher. */
    for( int direction = origcbp ? 1 : -1; direction >= -1; direction-=2 )
    {

    }

// rdo 中有个for 循环,意思是qp调整方向,是往大了调整,还是往小了调整,如果cbp全为0,表示没有残差了,就调小点,保留细节,如果cbp不为0就调大一点,尝试节省一些码率。

/* Check transform again; decision from before may no longer be optimal. */
    if( h->mb.i_qp != orig_qp && h->param.analyse.b_transform_8x8 &&
        x264_mb_transform_8x8_allowed( h ) )
    {
        h->mb.b_transform_8x8 ^= 1;
        cost = rd_cost_mb( h, a->i_lambda2 );
        if( cost > bcost )
            h->mb.b_transform_8x8 ^= 1;
    }

//调完后再做一次rd_mb_cost计算

static int rd_cost_mb( x264_t *h, int i_lambda2 )
{
    int b_transform_bak = h->mb.b_transform_8x8;
    int i_ssd;
    int i_bits;
    int type_bak = h->mb.i_type;

    x264_macroblock_encode( h );

} 这里重新编码了一次。

 

https://blog.csdn.net/fantasy_arm9/article/details/89538442

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值