【秒懂音視訊開發】23_H.264編碼

M了個J發表於2021-05-25

本文主要介紹一種非常流行的視訊編碼:H.264

計算一下:10秒鐘1080p(1920x1080)、30fps的YUV420P原始視訊,需要佔用多大的儲存空間?

  • (10 * 30) * (1920 * 1080) * 1.5 = 933120000位元組 ≈ 889.89MB
  • 可以看得出來,原始視訊的體積是非常巨大的

由於網路頻寬和硬碟儲存空間都是非常有限的,因此,需要先使用視訊編碼技術(比如H.264編碼)對原始視訊進行壓縮,然後再進行儲存和分發。H.264編碼的壓縮比可以達到至少是100:1。

簡介

H.264,又稱為MPEG-4 Part 10,Advanced Video Coding

  • 譯為:MPEG-4第10部分,高階視訊編碼
  • 簡稱:MPEG-4 AVC

H.264是迄今為止視訊錄製、壓縮和分發的最常用格式。截至2019年9月,已有91%的視訊開發人員使用了該格式。H.264提供了明顯優於以前任何標準的壓縮效能。H.264因其是藍光碟的其中一種編解碼標準而著名,所有藍光碟播放器都必須能解碼H.264。

編碼器

H.264標準允許製造廠商自由地開發具有競爭力的創新產品,它並沒有定義一個編碼器,而是定義了編碼器應該產生的輸出碼流。

x264是一款免費的高效能的H.264開源編碼器。x264編碼器在FFmpeg中的名稱是libx264

AVCodec *codec = avcodec_find_encoder_by_name("libx264");

解碼器

H.264標準中定義了一個解碼方法,但是製造廠商可以自由地開發可選的具有競爭力的、新的解碼器,前提是他們能夠獲得與標準中採用的方法同樣的結果。

FFmpeg預設已經內建了一個H.264的解碼器,名稱是h264

AVCodec *codec1 = avcodec_find_decoder_by_name("h264");

// 或者
AVCodec *codec2 = avcodec_find_decoder(AV_CODEC_ID_H264);

編碼過程與原理

H.264的程式設計過程比較複雜,本文只介紹大體的框架和脈絡,具體細節就不展開了。

大體可以歸納為以下幾個主要步驟:

  • 劃分幀型別
  • 幀內/幀間編碼
  • 變換 + 量化
  • 濾波
  • 熵編碼

劃分幀型別

有統計結果表明:在連續的幾幀影像中,一般只有10%以內的畫素有差別,亮度的差值變化不超過2%,而色度的差值變化只在1%以內。

GOP

於是可以將一串連續的相似的幀歸到一個影像群組(Group Of Pictures,GOP)。

GOP

GOP中的幀可以分為3種型別:

  • I幀(I Picture、I Frame、Intra Coded Picture),譯為:幀內編碼影像,也叫做關鍵幀(Keyframe)
    • 是視訊的第一幀,也是GOP的第一幀,一個GOP只有一個I幀
    • 編碼
      • 對整幀影像資料進行編碼
    • 解碼
      • 僅用當前I幀的編碼資料就可以解碼出完整的影像
    • 是一種自帶全部資訊的獨立幀,無需參考其他影像便可獨立進行解碼,可以簡單理解為一張靜態影像
  • P幀(I Picture、I Frame、Predictive Coded Picture),譯為:預測編碼影像
    • 編碼
      • 並不會對整幀影像資料進行編碼
      • 以前面的I幀或P幀作為參考幀,只編碼當前P幀與參考幀的差異資料
    • 解碼
      • 需要先解碼出前面的參考幀,再結合差異資料解碼出當前P幀完整的影像
  • B幀(B Picture、B Frame、Bipredictive Coded Picture),譯為:前後預測編碼影像
    • 編碼
      • 並不會對整幀影像資料進行編碼
      • 同時以前面、後面的I幀或P幀作為參考幀,只編碼當前B幀與前後參考幀的差異資料
      • 因為可參考的幀變多了,所以只需要儲存更少的差異資料
    • 解碼
      • 需要先解碼出前後的參考幀,再結合差異資料解碼出當前B幀完整的影像

不難看出,編碼後的資料大小:I幀 > P幀 > B幀。

顯示和編碼順序

在較早的視訊編碼標準(例如MPEG-2)中,P幀只能使用一個參考幀,而一些現代視訊編碼標準(比如H.264),允許使用多個參考幀。

多個參考幀

GOP的長度

GOP的長度表示GOP的幀數。GOP的長度需要控制在合理範圍,以平衡視訊質量、視訊大小(網路頻寬)和seek效果(拖動、快進的響應速度)等。

  • 加大GOP長度有利於減小視訊檔案大小,但也不宜設定過大,太大則會導致GOP後部幀的畫面失真,影響視訊質量

  • 由於P、B幀的複雜度大於I幀,GOP值過大,過多的P、B幀會影響編碼效率,使編碼效率降低

  • 如果設定過小的GOP值,視訊檔案會比較大,則需要提高視訊的輸出位元速率,以確保畫面質量不會降低,故會增加網路頻寬

  • GOP長度也是影響視訊seek響應速度的關鍵因素,seek時播放器需要定位到離指定位置最近的前一個I幀,如果GOP太大意味著距離指定位置可能越遠(需要解碼的參考幀就越多)、seek響應的時間(緩衝時間)也越長

GOP的型別

GOP又可以分為開放(Open)、封閉(Closed)兩種。

  • Open
    • 前一個GOP的B幀可以參考下一個GOP的I幀
  • Closed
    • 前一個GOP的B幀不能參考下一個GOP的I幀
    • GOP不能以B幀結尾

長度為15的Open GOP

長度為15的Closed GOP

需要注意的是:

  • 由於P幀、B幀都對前面的參考幀(P幀、I幀)有依賴性,因此,一旦前面的參考幀出現資料錯誤,就會導致後面的P幀、B幀也出現資料錯誤,而且這種錯誤還會繼續向後傳播

  • 對於普通的I幀,其後的P幀和B幀可以參考該普通I幀之前的其他I幀

在Closed GOP中,有一種特殊的I幀,叫做IDR幀(Instantaneous Decoder Refresh,譯為:即時解碼重新整理)。

  • 當遇到IDR幀時,會清空參考幀佇列
  • 如果前一個序列出現重大錯誤,在這裡可以獲得重新同步的機會,使錯誤不會繼續往下傳播
  • 一個IDR幀之後的所有幀,永遠都不會參考該IDR幀之前的幀
  • 視訊播放時,播放器一般都支援隨機seek(拖動)到指定位置,而播放器直接選擇到指定位置附近的IDR幀進行播放最為便捷,因為可以明確知道該IDR幀之後的所有幀都不會參考其之前的其他I幀,從而避免較為複雜的反向解析

IDR

幀內/幀間編碼

I幀採用的是幀內(Intra Frame)編碼,處理的是空間冗餘。
P幀、B幀採用的是幀間(Inter Frame)編碼,處理的是時間冗餘。

劃分巨集塊

在進行編碼之前,首先要將一張完整的幀切割成多個巨集塊(Macroblock),H.264中的巨集塊大小通常是16x16。

巨集塊可以進一步拆分為多個更小的變換塊(Transform blocks)、預測塊(Prediction blocks)。

  • 變換塊的尺寸有:16x16、8x8、4x4

  • 預測塊的尺寸有:16×16、16×8、8×16、8×8、8×4、4×8、4×4

預測塊

幀內編碼

幀內編碼,也稱幀內預測。以4x4的預測塊為例,共有9種可選的預測模式。

預測模式

預測模式描述

利用幀內預測技術,可以得到預測幀,最終只需要保留預測模式資訊、以及預測幀與原始幀的殘差值。

編碼器會選取最佳預測模式,使預測幀更加接近原始幀,減少相互間的差異,提高編碼的壓縮效率。

幀間編碼

幀間編碼,也稱幀間預測,用到了運動補償(Motion compensation)技術。

編碼器利用塊匹配演算法,嘗試在先前已編碼的幀(稱為參考幀)上搜尋與正在編碼的塊相似的塊。如果編碼器搜尋成功,則可以使用稱為運動向量的向量對塊進行編碼,該向量指向匹配塊在參考幀處的位置。

在大多數情況下,編碼器將成功執行,但是找到的塊可能與它正在編碼的塊不完全匹配。這就是編碼器將計算它們之間差異的原因。這些殘差值稱為預測誤差,需要進行變換並將其傳送給解碼器。

綜上所述,如果編碼器在參考幀上成功找到匹配塊,它將獲得指向匹配塊的運動向量和預測誤差。使用這兩個元素,解碼器將能夠恢復該塊的原始畫素。

如果一切順利,該演算法將能夠找到一個幾乎沒有預測誤差的匹配塊,因此,一旦進行變換,運動向量加上預測誤差的總大小將小於原始編碼的大小。

如果塊匹配演算法未能找到合適的匹配,則預測誤差將是可觀的。因此,運動向量的總大小加上預測誤差將大於原始編碼。在這種情況下,編碼器將產生異常,併為該特定塊傳送原始編碼。

變換與量化

接下來對殘差值進行DCT變換(Discrete Cosine Transform,譯為離散餘弦變換)。

規格

H.264的主要規格有:

  • Baseline Profile(BP)
    • 支援I/P幀,只支援無交錯(Progressive)和CAVLC
    • 一般用於低階或需要額外容錯的應用,比如視訊通話、手機視訊等即時通訊領域
  • Extended Profile(XP)
    • 在Baseline的基礎上增加了額外的功能,支援流之間的切換,改進誤碼效能
    • 支援I/P/B/SP/SI幀,只支援無交錯(Progressive)和CAVLC
    • 適合於視訊流在網路上的傳輸場合,比如視訊點播
  • Main Profile(MP)
    • 提供I/P/B幀,支援無交錯(Progressive)和交錯(Interlaced),支援CAVLC和CABAC
    • 用於主流消費類電子產品規格如低解碼(相對而言)的MP4、便攜的視訊播放器、PSP和iPod等
  • High Profile(HiP)
    • 最常用的規格
    • 在Main的基礎上增加了8x8內部預測、自定義量化、無損視訊編碼和更多的YUV格式(如4:4:4)
      • High 4:2:2 Profile(Hi422P)
      • High 4:4:4 Predictive Profile(Hi444PP)
      • High 4:2:2 Intra Profile
      • High 4:4:4 Intra Profile
    • 用於廣播及視訊碟片儲存(藍光影片),高清電視的應用

相關文章