音視頻編程基本概念梳理

本文梳理了音視頻編程開發者須要瞭解的基本概念
訪問 個人博客瞭解更多

前言

本文梳理了音視頻編程開發者須要瞭解的基本概念,固然,有的人一開始看着乾巴巴的理論,感到睏乏,倒是一個喜歡動手實踐的開發者,那麼先實踐 ffmpeg的C語言編程入門,而後再來看理論篇更好了。算法

音頻的基本概念

音頻技術是爲了採樣、存儲、播放"聲學現象"而存在的,詳細一點,是模擬信號與數字信號轉換;在人耳可聽的時域與頻域的範圍內,進行壓縮、轉碼,在數據大小與音質的取捨中存儲音頻文件;播放時解讀文件的音頻參數,進行轉碼。編程

聲學的物理知識

聲音是有物體振動而產生的,是一種壓力波。網絡

聲音的振動會引發空氣有節奏的振動,是周圍的空氣發生疏密變化,造成疏密相間的縱波

經過上一句話,容易理解聲波三要素:工具

  • 頻率,音階的高低,頻率越高,波長越短,而低頻聲音的波長較長,更容易繞過阻礙物。
  • 振幅,響度,使用分貝描述響度的大小,
  • 波形,音色

人耳的生物知識

回聲的區分:兩道聲音傳入人耳的時差小於 80 毫秒,人耳便沒法區分這兩道聲音。性能

人耳可接收的頻率範圍:20Hz~20kHz測試

聲音的數字化

數字音頻的三個要素: 採樣、量化、編碼優化

  • 採樣,在時間軸上對信號進行數字化,根據採樣定理(奈奎斯特定理),按比聲音最高頻率高兩倍以上的頻率對聲音進行採樣(AD轉換),根據人耳可聽頻率,高質量的採樣頻率爲 44.1kHz,即一秒採樣44100次
  • 量化,在幅度軸上對信號進行數字化,例如使用 short (16 bit) 存儲空間表示一個聲音採樣,共有 2^16 個可能取值,因而模擬的音頻信號在幅度上分爲了 65536 層
  • 編碼,按照必定的格式記錄採樣和量化後的數字數據,好比順序存儲,壓縮存儲等

音頻文件的原始格式,PCM, WAV編碼

PCM + WAV header (44 bit) = WAVspa

PCM 全稱 Pulse Code Modulation,脈衝編碼調製,是音頻的裸數據,PCM 文件缺乏描述參數,通常須要 WAV header 來描述,如:量化格式(sampleFormat)、採樣率(sampleRate)、聲道數(channel)。設計

wav header

描述音頻文件的大小、質量

  • 比特率,對於聲音格式,一個常見的描述大小的概念是,數據比特率,描述一秒時間內的比特數目,能夠做爲衡量音頻質量的依據。
  • 採樣格式,好比用16 bit,即 4 字節來描述一個採樣,存儲空間越大,聲音在頻域上描述越精細。
  • 採樣率,好比 48kHz,採樣率越大,聲音在時域上描述越精細。

計算比特率的公式: 採樣率 × 採樣格式 × 聲道數 = 比特率

聲音的大小單位——分貝

什麼是分貝,爲何使用分貝做單位?

若以聲壓值來表示聲音大小,變化範圍太大,能夠達到六個數量級以上,另外,人耳對聲音信號的強弱刺激的反應不是線性的,而是呈對數比例關係,因而採用分貝的概念:

分貝是指兩個物理量之比除以 10 爲底的對數並乘以 10,中文描述有點繞,看簡潔的公式

N = 10 * lg(A1/A0)

分貝符號:dB, 它是無量綱的,式中 A0 是基準量,A1是"被量度"量

音頻的編碼

CD 音質的格式是 WAV,完整地存儲採樣數據。可是存儲空間較大,計算一下,CD的音質參數:量化格式16 bit,採樣率 44100,聲道數 2,計算一秒的比特數:

44100 16 2 = 1378.125 kbps (千比特每秒) = 176400 字節每秒

一分鐘的 CD 音質的存儲空間約爲 10.09 MB。存儲空間太大,不適合在 4G 如下的網絡中在線播放音頻。

在實際應用中,須要對數據進行壓縮,有效的壓縮方法是從兩個維度上進行壓縮,分別是頻域與時域。

提供給人類播放的音頻,只需保存人耳聽覺範圍內的信號,因而音頻壓縮編碼的原理其實是壓縮掉冗餘信號,冗餘信號包括人耳聽覺範圍以外的音頻信號以及被掩蔽掉的音頻信號等,被掩蔽掉的音頻信號主要是由於人耳的掩蔽效應,主要表現爲頻域掩蔽效應與時域掩蔽效應,不管是時域上仍是頻域上,被掩蔽掉的聲音信號都被認爲是冗餘信息,不進行編碼處理。

介紹常見的音頻格式:

  • MP3,具備不錯的壓縮比,MP3其中一種實現編碼格式 LAME 是中高碼率的,聽感接近源 WAV 文件。MP3適用於在高比特率下有兼容要求的音樂欣賞。
  • ACC,新一代音頻有損壓縮技術,在小於 128 Kbit/s的碼率下表現優異,多用於視頻中音頻軌的編碼。
  • Ogg,開源免費,在各類碼率下都有比較優秀的表現,表現優於 MP3,缺點是兼容性不夠好,不支持流媒體特性,適用於語音聊天的音頻消息場景。

視頻的基本概念

表示方式

常見兩種表示方式爲: RGB, YUV

RGB 概念

RGB的概念,不少人都瞭解,三種原色來描述一個像素點,還有 RGBA 格式,A 是透明度。

像素的取值範圍有幾種:

  • 浮點數,取值範圍 0.0 ~ 1.0,例如 OpenGL ES
  • 整數,子像素的取值範圍 0~255,或 00 ~ FF, 這是計算機上的 8 bit, RGBA 四個子像素即佔用 32 bit,即 4 個字節,這是 RGBA_8888,也有特別的表示方法,好比安卓平臺上的 RGB_565,16 bit 表示一個像素,R=5 bit, G=6 bit, B=5 bit

一張圖片的裸數據是 bitmap,內存很大,也浪費空間,因而有壓縮算法:

JPEG 是靜態圖像壓縮標準,有良好的壓縮性能,然而,對於視頻來講還不夠,視頻還須要在時域上進行壓縮,後面講到。

YUV 概念

若是你未理解過 YUV 概念,來看這一張熟悉的圖片:

90年代彩色電視或黑白電視,測試畫面使用的圖片,圖片的色塊直接地反映了 YUV 的色彩空間,再來看下一張端口圖:

以上端口中,老式的黑白電視使用 Y C 端口,彩色電視採用 YUV 端口,之前在家接過電視盒、DVD端口的童鞋是否是很熟悉。其中 Y 表明明亮度/灰階值 (Luma);U 和 V 表明色度(chroma),指定像素的顏色。

歸納而言,YUV 主要應用於優化彩色視頻信號的傳輸,使其向後兼容老式黑白電視。

與直觀的 RGB 不一樣,YUV 的表示方式是差分的:

  • Y 亮度,是 RGB 信號的特定部分疊加到一塊兒的值
  • U V 色度,分別是色調 Cr 與飽和度 Cb,Cr 表示 RGB 紅色部分與亮度值的差別,Cb表示 RGB 藍色部分與亮度值的差別

看下一張圖片反映 YUV 與 RGB 的差別

YUV 最多見的採樣格式是 4:2:0,其中 0 不表明其中一個輸入爲0,而是交錯的 4:2:0 與 4:0:2,左右兩列的色度是共享的,以下圖片

不考慮時域壓縮,YUV的一幀圖片比RGB的一幀圖片的比特量化要大,好比 RGB 用 8 bit 表示一個像素,YUV 須要用 12 bit 表示一個像素。

瞭解 YUV 的概念,對於音視頻編程中的客戶端開發,是必要的。在IOS或安卓,攝像頭採集到的裸數據格式是 YUV,而後須要調用相關API使其轉換成 RGB 格式,詳細暫且打住。

視頻編碼

音視頻的編碼一般是去除冗餘信息,從而實現數據量的壓縮。對於視頻,能夠從空間與時間維度上進行壓縮,並且,視頻數據有極強的相關性,有着大量的冗餘信息。

從時間維度上去除冗餘信息的方法:

  • 運動補償,經過先前的局部圖像來預測、補償當前的局部圖像
  • 運動表示,不一樣區域的圖像須要使用不一樣的運動矢量來描述運動信息
  • 運動估計,從視頻序列中抽取運動信息的一整套技術

從空間維度上,運用幀內編碼技術,例如,靜態圖像編碼標準 JPEG,在視頻上,ISO 制定了 Motion JPEG,即 MPEG,MPEG算法是適用於動態視頻的壓縮算法,除了對單幅圖像進行編碼外,還利用圖像序列中相關原則去除冗餘,大大提升壓縮比。MPEG版本一直在不斷更新,如:Mpeg1(用於VCD),Mpeg2(用於DVD),Mpeg4 AVC(流媒體的主力算法)

獨立於 ISO 制定的 MPEG 視頻壓縮標準,ITU-T制定了 H.261~H.264一系列視頻標準,其中 H.264吸收了衆多標準的經驗,採起簡約設計,比起 Mpeg4更容易推廣。

H.264使用了新的壓縮技術,例如:多參考幀,多塊類型,整數變換,幀內預測等,使用了更精細的分像素運動矢量(1/4,1/8)和新一代的環路濾波器。

編碼的細節概念

IPB 幀,是最多見的幀間編碼技術類型,在GOP(Group Of Pictures)中有如下三種幀:

  • I 幀,intra picture,幀內編碼幀,I幀一般是每一個 GOP 的第一個幀,進過適度壓縮,做爲隨機訪問的參考點,能夠當作靜態圖像。I幀壓縮能夠去掉視頻的空間冗餘信息。
  • P 幀,predictive picture,前向預測編碼幀,經過將圖像序列中前面已編碼幀的時間冗餘信息充分去除壓縮傳播數量的編碼圖像,簡稱預測幀。
  • B 幀,bi-directional interpolated prediction frame,雙向預測內插編碼幀,與P幀不一樣的是,它同時參考圖像序列前面與後面的已編碼幀的時間冗餘信息。

gop_size,表明兩個 I 幀之間的幀數目。理論上,在存儲空間固定的條件下,gop_size越大,畫面質量越好,由於能夠留下更多的空間存儲畫質更高的 I 幀。

壓縮比,通常而言,I幀的壓縮率是 7 (與 JPG 差很少),P幀是20,B幀是50

PTS 與 DTS

  • DTS, decode timestamp,數據壓縮包 packet 的解碼時間
  • PTS, presentation timestamp,視頻幀 frame 的展現時間

通常來講,若是視頻的各幀編碼是按輸入順序依次進行的,那麼解碼時間與顯示時間應該一致,然而事實上,大多數編解碼標準(如H.264),編碼順序與顯示順序並不一致,因而須要 PTS 與 DTS 兩種時間戳。

Tip: 在 FFmpeg 工具中,AVPacket結構體是描述解碼前或編碼後的壓縮數據,AVFrame是描述視頻的一幀圖像,而 DTS 是 AVPacket 結構體的一個成員屬性,PTS 是 AVFrame 的一個成員屬性。另外,FFmpeg 中還有一個屬性,基準時間 time_base ,即每 1 pts 的時間間隔,單位秒

Reference

本文的文字摘抄於《音視頻開發進階指南》,便是我閱讀後將知識內化的再輸出

圖片均來自互聯網

相關文章
相關標籤/搜索