5.2.3 Y模式解码
作者:chai51
出处:https://www.cnblogs.com/chai51
版权:本文版权归作者和博客园共有
转载:欢迎转载,但未经作者同意,必须保留此段声明;必须在文章中给出原文连接;否则必究法律责任
引言
Y模式解码是帧间预测模式信息解码的核心步骤,它确定当前块使用的预测模式类型(NEWMV、NEARESTMV、NEARMV、GLOBALMV等)。Y模式的选择决定了如何获取和使用运动向量。
源码说明: 本文档基于作者自己编写的AV1解码器Python实现,所有代码示例和实现细节均来自实际可运行的源码。源码仓库:GitHub - av1_learning
Y模式解码概述
位置: src/tile/tile_group.py - __inter_block_mode_info()
功能说明
Y模式解码确定当前块使用的预测模式类型,包括NEWMV、NEARESTMV、NEARMV、GLOBALMV等模式。
模式类型
- NEWMV / NEW_NEWMV: 新运动向量,需要解码MV差值
- NEARESTMV / NEAREST_NEARESTMV: 使用最近的候选MV
- NEARMV / NEAR_NEARMV: 使用近邻候选MV
- GLOBALMV / GLOBAL_GLOBALMV: 使用全局运动参数
- NEAR_NEWMV / NEW_NEARMV: 混合模式
解码流程
# 1. 检查skip_mode
if skip_mode == 1:
YMode = NEAREST_NEARESTMV
# 2. 检查分段特征
elif segment_feature_enabled(SEG_LVL_SKIP) or segment_feature_enabled(SEG_LVL_GLOBALMV):
YMode = GLOBALMV
# 3. 如果是复合预测
elif isCompound:
compound_mode = read_S(av1, 'compound_mode')
YMode = NEAREST_NEARESTMV + compound_mode
# 4. 单参考模式
else:
new_mv = read_S(av1, 'new_mv')
if new_mv == 0:
YMode = NEWMV
else:
zero_mv = read_S(av1, 'zero_mv')
if zero_mv == 0:
YMode = GLOBALMV
else:
ref_mv = read_S(av1, 'ref_mv')
YMode = NEARESTMV if ref_mv == 0 else NEARMV
Y模式解码流程图
Y模式解码主流程
graph TD
A[Y模式解码开始<br/>__inter_block_mode_info] --> B[初始化调色板大小<br/>PaletteSizeY = 0<br/>PaletteSizeUV = 0]
B --> C[解码参考帧<br/>__read_ref_frames]
C --> D[构建MV栈<br/>find_mv_stack]
D --> E[计算复合预测]
E --> F{skip_mode == 1?}
F -->|是| G[NEAREST_NEARESTMV]
F -->|否| H{分段特征<br/>SEG_LVL_SKIP<br/>或SEG_LVL_GLOBALMV?}
G --> REF[解码RefMvIdx]
H -->|是| I[GLOBALMV]
H -->|否| J{复合预测?}
I --> REF
J -->|是| K[解码compound_mode]
J -->|否| L[单参考模式解码]
K --> M[NEAREST_NEARESTMV + compound_mode]
M --> REF
L --> N[解码new_mv]
N --> O{new_mv == 0?}
O -->|是| P[NEWMV]
O -->|否| Q[解码zero_mv]
P --> REF
Q --> R{zero_mv == 0?}
R -->|是| S[GLOBALMV]
R -->|否| T[解码ref_mv]
S --> REF
T --> U{ref_mv == 0?}
U -->|是| V[NEARESTMV]
U -->|否| W[NEARMV]
V --> REF
W --> REF
REF --> ASSIGN[分配运动向量<br/>__assign_mv]
ASSIGN --> INTERINTRA[解码Inter-Intra模式<br/>__read_interintra_mode]
INTERINTRA --> MOTION[解码运动模式<br/>__read_motion_mode]
MOTION --> COMPOUND[解码复合类型<br/>__read_compound_type]
COMPOUND --> FILTER[解码插值滤波器]
FILTER --> END[Y模式解码完成]
style A fill:#e1f5ff
style F fill:#fff9c4
style H fill:#fff9c4
style J fill:#fff9c4
style O fill:#fff9c4
style R fill:#fff9c4
style U fill:#fff9c4
style END fill:#c8e6c9
详细技术文档参考
说明: 以下内容来自详细技术文档,包含完整的实现细节和代码说明。这些内容主要用于技术参考。
点击展开查看详细技术文档
RefMvIdx解码流程(DRL模式)
graph TD
A[RefMvIdx解码开始] --> B[RefMvIdx = 0]
B --> C{YMode类型}
C -->|NEWMV<br/>NEW_NEWMV| D[DRL模式解码NEWMV]
C -->|NEARMV<br/>NEAR_NEARMV<br/>NEAR_NEWMV<br/>NEW_NEARMV| E[DRL模式解码NEARMV]
C -->|其他| F[RefMvIdx保持为0]
D --> D1{MV候选数量少于2个?}
D1 -->|是| D2[解码drl_mode idx=0]
D1 -->|否| D3[RefMvIdx = 0]
D2 --> D4{drl_mode == 0?}
D4 -->|是| D5[RefMvIdx = 0]
D4 -->|否| D6[RefMvIdx = 1]
D6 --> D7{MV候选数量大于2个?}
D7 -->|是| D8[解码drl_mode idx=1]
D7 -->|否| D9[RefMvIdx = 1]
D8 --> D10{drl_mode == 0?}
D10 -->|是| D11[RefMvIdx = 1]
D10 -->|否| D12[RefMvIdx = 2]
D3 --> END
D5 --> END
D9 --> END
D11 --> END
D12 --> END
E --> E1[RefMvIdx = 1]
E1 --> E2{MV候选数量大于2个?}
E2 -->|是| E3[解码drl_mode idx=1]
E2 -->|否| E4[RefMvIdx = 1]
E3 --> E5{drl_mode == 0?}
E5 -->|是| E6[RefMvIdx = 1]
E5 -->|否| E7[RefMvIdx = 2]
E7 --> E8{MV候选数量大于3个?}
E8 -->|是| E9[解码drl_mode idx=2]
E8 -->|否| E10[RefMvIdx = 2]
E9 --> E11{drl_mode == 0?}
E11 -->|是| E12[RefMvIdx = 2]
E11 -->|否| E13[RefMvIdx = 3]
E4 --> END
E6 --> END
E10 --> END
E12 --> END
E13 --> END
F --> END[RefMvIdx解码完成]
style A fill:#e1f5ff
style C fill:#fff9c4
style D4 fill:#fff9c4
style D10 fill:#fff9c4
style E5 fill:#fff9c4
style E11 fill:#fff9c4
style END fill:#c8e6c9
总结
Y模式解码确定当前块使用的预测模式类型,是帧间预测模式信息解码的核心步骤。不同的Y模式对应不同的MV获取方式,直接影响后续的运动向量分配。
参考资源:
- AV1规范文档
- 源码实现: GitHub - av1_learning
- Tile解码:
src/tile/tile_group.py
- Tile解码:

浙公网安备 33010602011771号