1. 程式人生 > >【RNNoise】用深度學習抑制噪聲

【RNNoise】用深度學習抑制噪聲

RNNoise: Learning Noise Suppression

原文連結:https://people.xiph.org/~jm/demo/rnnoise/
Banner

上圖顯示了前後音訊(移動滑鼠時)噪聲抑制的頻譜圖。

這是RNNoise 該演示介紹了RNNoise專案,顯示瞭如何將深度學習應用於噪聲抑制。主要思想是將經典訊號處理與深度學習結合起來,建立一個小而快速的實時噪聲抑制演算法。不需要昂貴的GPU,可以在Raspberry Pi上輕鬆執行。結果更簡單(更容易調諧),聽起來比傳統的噪音抑制系統更好(已經有!)。 噪聲抑制 噪音抑制是言語處理中的一個相當古老的話題,至少可以追溯到70年代。顧名思義,這個想法是採取嘈雜的訊號,並儘可能多地消除噪音,同時對感興趣的言論造成最小的失真。

traditional noise suppression

傳統噪音抑制 這是傳統噪聲抑制演算法的概念圖。語音活動檢測(VAD)模組檢測訊號何時包含聲音以及何時只是噪聲。這被噪聲譜估計模組用於計算噪聲的頻譜特性(每個頻率多少功率)。然後,知道噪聲如何,它可以從輸入音訊“減去”(不像聽起來那麼簡單)。 從上圖看,噪聲抑制看起來很簡單:只是三個概念上簡單的任務,我們完成了,對吧?對與錯!任何本科EE學生都可以寫一個噪音抑制演算法,有時候...有些...困難的部分是使其工作正常,所有的時間,各種噪音。這需要非常仔細地調整演算法中的每個旋鈕,許多特殊情況用於奇怪的訊號和大量的測試。總有一些奇怪的訊號會導致問題,需要更多的調優,並且比您修復更容易破解更多的東西。科學50%,藝術50%。我以前在speexdsp庫中的噪音抑制器。這有點工作,但不是很好。
深度學習和反覆神經網路
深層次學習是一種新思想的新版本:人工神經網路。雖然自六十年代以來一直存在,近年來有什麼新的呢?


我們現在知道如何使它們比兩個隱藏層更深
我們知道如何使復發網路在過去很長時間記住模式
我們有實際訓練他們的計算資源
迴圈神經網路(RNN)在這裡非常重要,因為它們可以對時間序列建模,而不是僅僅考慮輸入和輸出幀。這對噪聲抑制特別重要,因為我們需要時間來獲得良好的噪聲估計。很長時間以來,RNN的能力受到很大的限制,因為它們長期不能儲存資訊,並且由於當通過時間反向傳播時涉及的梯度下降過程是非常低效的(消失的梯度問題)。這兩個問題都通過發明門控單元來解決,如長期記憶(LSTM),門控迴圈單元(GRU)及其許多變體。
RNNoise使用門控迴圈單元(GRU),因為它在此任務上執行得比LSTM略好,並且需要更少的資源(CPU和儲存器的權重)。與簡單的迴圈單元相比,GRU有兩個額外的門。復位門控制狀態(儲存器)是否用於計算新狀態,而更新門控制狀態將根據新輸入而改變多少。這個更新門(關閉時)使得GRU可以長時間地記住資訊(和簡單的),這是GRU(和LSTM)比簡單的迴圈單元執行得更好的原因。
recurrent units
Comparing a simple recurrent unit with a GRU. The difference lies in the GRU's r and zgates, which make it possible to learn longer-term patterns. Both are soft switches (value between 0 and 1) computed based on the previous state of the whole layer and the inputs, with a sigmoid activation function. When the update gate 
z is on the left, then the state can remain constant over a long period of time — until a condition causes z to switch to the right.
經常性單位
將簡單的迴圈單元與GRU進行比較。區別在於GRU的r和z門,這使得有可能學習更長期的模式。兩者都是基於整個層的先前狀態和輸入計算的軟開關(0到1之間的值),具有S形啟用功能。當更新門z在左邊時,狀態可以在很長一段時間內保持恆定,直到一個條件使z轉向右邊。
混合方法
由於深入學習的成功,現在在整個問題中丟擲深層神經網路是很受歡迎的。這些方法稱為端到端 - 這是神經元一直下降。端對端方法已被應用於語音識別和語音合成一方面,這些端到端系統已經證明了深層神經網路可以有多強大。另一方面,這些系統有時可能是次要的,而且在資源方面是浪費的。例如,噪聲抑制的一些方法使用具有數千個神經元和數千萬個權重的層來執行噪聲抑制。缺點是不僅執行網路的計算成本,還有模型本身的大小,因為您的磁帶庫現在有數千行程式碼以及幾十兆位元組(如果不是更多)的神經元權重。
這就是為什麼我們在這裡採用不同的方法:保持所有需要的基本訊號處理(沒有神經網路嘗試模擬它),但讓神經網路學習所有需要不必要的調整的棘手部分,旁邊的訊號處理。另一件與現有的深入學習噪音抑制工作不同的是,我們的目標是實時通訊而不是語音識別,所以我們不能超過幾毫秒(在這種情況下為10毫秒) 。

單位定義問題


為了避免產生大量的輸出 - 因此大量的神經元 - 我們決定不直接使用樣本或頻譜。相反,我們考慮遵循巴克量表的頻段,一個與我們感知到的聲音相匹配的頻率比例。我們使用總共22個頻段,而不是480(複雜)頻譜值,我們將不得不考慮。

frequency bands Layout of the Opus bands vs the actual Bark scale. For RNNoise, we use the same base layout as Opus. Since we overlap the bands, the boundaries between the Opus bands become the center of the overlapped RNNoise bands. The bands are wider at higher frequency because the ear has poorer frequency resolution there. At low frequencies, the bands are narrower, but not as narrow as the Bark scale would give because then we would not have enough data to make good estimates

Opus樂隊的佈局與實際的Bark比例。對於RNNoise,我們使用與Opus相同的基本佈局。由於我們與樂隊重疊,Opus樂隊之間的界限成為重疊的RNNoise樂隊的中心。由於耳朵在那裡的頻率解析度較差,頻段的頻率較高。在低頻下,樂隊更窄,但並不像巴克比例那樣窄,因為我們沒有足夠的資料來做出很好的估計。
當然,我們無法從22個頻段的能量重建音訊。我們可以做的是計算一個應用於每個頻帶訊號的增益。您可以將其視為使用22頻段均衡器,並快速更改每個頻段的電平,以便衰減噪聲,但讓訊號通過。


使用每頻帶增益有幾個優點。首先,它使得一個更簡單的模型,因為有更少的樂隊計算。第二,它不可能產生所謂的音樂噪聲偽影,其中只有單個音調在其鄰居被衰減的同時才能通過。這些文物在噪音抑制中很常見,相當煩人。要是足夠寬闊的樂隊,我們要麼讓整個樂隊穿過,要麼全部剪下來。第三個優點來自於我們如何優化模型。由於增益總是在0和1之間,所以簡單地使用S形啟用函式(其輸出也在0和1之間)來計算它們確保我們永遠不會做一些非常愚蠢的事情,比如新增不在第一名。

對於輸出,我們還可以選擇整流的線性啟用函式來表示在0和無窮大之間的dB的衰減。 為了更好地優化訓練中的增益,損失函式是應用於提高到功率α的增益的均方誤差(MSE)。 到目前為止,我們發現α= 0.5在感知上產生最好的結果。 使用α→0將等效於最小化對數光譜距離,並且是有問題的,因為最佳增益可以非常接近零。

我們從使用頻帶獲得的較低解析度的主要缺點是我們沒有足夠好的解析度來抑制音調諧波之間的噪聲。幸運的是,它不是那麼重要,甚至是一個簡單的技巧(見下面的音調濾波部分)。


由於我們計算的輸出是基於22個頻段,所以輸入頻率解析度更高是沒有意義的,所以我們使用相同的22個頻帶將頻譜資訊提供給神經網路。因為音訊具有巨大的動態範圍,所以計算能量的日誌而不是直接饋送能量要好得多。而在我們這樣做的時候,它永遠不會用DCT來去除相關的特徵。所得到的資料是基於Bark量表的倒譜,其與語音識別中非常常用的Mel-Frequency倒譜系數(MFCC)密切相關。


除了我們的倒譜系數,我們還包括:


前6個係數跨幀的第一和第二個導數
音調週期(1 /基頻)
6個樂隊的音高(聲音強度)
一種特殊的非平穩性值,可用於檢測語音(但超出本演示範圍)
這使得神經網路共有42個輸入特徵。


深層建築


我們使用的深層建築靈感源於傳統的噪音抑制方法。大部分工作是由3個GRU層完成的。下圖顯示了我們用於計算頻帶增益的層次,以及架構如何對映到噪聲抑制中的傳統步驟。當然,像神經網路通常情況一樣,我們沒有實際的證據證明網路正在使用它的層次,而是我們嘗試的拓撲結構比其他人更好的事實使得認為它的行為與我們設計的一樣它。
network topology Topology of the neural network used in this project. Each box represents a layer of neurons, with the number of units indicated in parentheses. Dense layers are fully-connected, non-recurrent layers. One of the outputs of the network is a set of gains to apply at different frequencies. The other output is a voice activity probability, which is not used for noise suppression but is a useful by-product of the network.

這些都是關於資料的
   有時甚至深層神經網路也可能很笨。 他們非常擅長他們所瞭解的知識,但是他們可能會對他們所知道的投入產生驚人的錯誤。 更糟糕的是,他們真的很懶惰的學生。 如果他們可以在訓練過程中使用任何漏洞,以避免學習困難,那麼他們會。 這就是為什麼訓練資料的質量至關重要。

一個廣為流傳的故事是,很久以前,一些軍隊的研究人員正試圖訓練一個神經網路來識別在樹上偽裝的坦克。 他們拍攝了有和沒有坦克的樹木,然後訓練了一個神經網路來識別那些有坦克的人。 網路成功超越了預期! 只有一個問題。 由於有坦克的照片是在多雲的天氣下拍攝的,而沒有坦克的照片是在陽光明媚的日子拍攝的,所以網路真正學到的是如何從陽光燦爛的日子開始陰天。 雖然研究人員現在意識到了這個問題,並避免了這樣明顯的錯誤,但它們的更微妙的版本仍然會發生(而且在過去已經發生了)。

在噪聲抑制的情況下,我們不能僅僅收集可用於監督學習的輸入/輸出資料,因為我們很少同時獲得乾淨的語音和嘈雜的語音。 相反,我們必須從清晰的語音和噪音的單獨記錄中人為地建立資料。 棘手的部分是獲得各種各樣的噪音資料,以增加語音。 我們還必須確保覆蓋各種錄音條件。 例如,僅在全頻段音訊(0-20 kHz)下訓練的早期版本將在8 kHz低通濾波時失效。

與語音識別常見的不同,我們選擇不將倒譜平均歸一化應用於我們的特徵,並保留代表能量的第一個倒譜系數。 因此,我們必須確保資料包括所有現實級別的音訊。 我們還對音訊應用隨機濾波器,使系統對各種麥克風頻率響應(通常由倒譜平均歸一化處理)具有魯棒性。

間距濾波


由於我們的頻帶的頻率解析度太粗,無法濾除音調諧波之間的噪聲,所以我們使用基本的訊號處理。 這是混合方式的另一部分。 當有相同變數的多個測量值時,提高精度(降低噪聲)的最簡單方法就是計算平均值。 顯然,只是計算相鄰音訊樣本的平均值不是我們想要的,因為它會導致低通濾波。 然而,當訊號是週期性的(例如有聲語音)時,我們可以計算由音調週期偏移的取樣的平均值。 這導致梳狀濾波器,其使音調諧波通過,同時衰減它們之間的頻率 - 噪聲在哪裡。 為了避免訊號失真,對於每個頻帶,梳狀濾波器被獨立地應用,並且其濾波器強度取決於音調相關性和神經網路計算的頻帶增益。

我們目前使用FIR濾波器進行音高濾波,但也可以(並在TODO列表中)使用IIR濾波器,如果強度太高,則會導致更高的失真風險,從而產生較大的噪聲衰減。

從Python到C


神經網路的所有設計和訓練都是使用真棒的Keras深度學習庫在Python中完成的。由於Python通常不是實時系統的首選語言,所以我們必須在C中實現執行時程式碼。幸運的是,執行神經網路比培訓一個簡單得多,所以我們只需要實現feed前向和GRU層。為了更輕鬆地將重量適合於合理的佔地面積,我們在訓練期間將權重的大小限制為+/- 0.5,這使得可以使用8位值輕鬆儲存它們。所得到的模型僅適用於85 kB(而不是將重量儲存為32位浮點數所需的340 kB)。


C程式碼可以使用BSD許可證。儘管在撰寫本簡報時,程式碼尚未優化,但它在x86 CPU上的執行速度比實時性要快60倍。它甚至比Raspberry Pi 3上的實時速度快7倍。具有良好的向量化(SSE / AVX),應該可以使其比現在快四倍。


給我看樣品!
好的,這很好,所有,但它實際上是如何發聲的?以下是RNNoise的一些例項,可以消除三種不同型別的噪音。在訓練期間都不使用噪音和乾淨的講話。

Suppression algorithm

 
  • No suppression 
  • RNNoise 
  • Speexdsp

Noise level (SNR)

 
  • 0 dB 
  • 5 dB 
  • 10 dB 
  • 15 dB 
  • 20 dB 
  • Clean

Noise type

 
  • Babble noise 
  • Car noise 
  • Street noise

選擇新樣本時選擇開始播放的位置

Evaluating the effect of RNNoise compared to no suppression and to the Speexdsp noise suppressor. Although the SNRs provided go as low as 0 dB, most applications we are targeting (e.g. WebRTC calls) tend to have SNRs closer to 20 dB than to 0 dB. 

那麼你應該聽什麼呢?聽起來很奇怪,你不應該期待著增加清晰度。人類非常善於理解噪音中的語音,增強演算法(特別是不允許前瞻性地去除噪聲的演算法)只能破壞資訊。那麼為什麼我們這樣做呢?為了質量增強的言論聽起來更不方便,可能導致聽眾疲勞減輕。


實際上,還有幾個實際上可以幫助清晰度的情況。第一種是視訊會議,當多個揚聲器混合在一起時。對於該應用,噪聲抑制可防止所有非活動揚聲器的噪聲與主動揚聲器混合,從而提高質量和可讀性。第二種情況是當語音通過低位元率編解碼器時。那些傾向於降低嘈雜的語音,而不是乾淨的語音,所以刪除噪音可以使編解碼器做得更好。
嘗試在你的聲音!


對上述樣品不滿意? 您可以從麥克風實際錄製,並使您的音訊實時降噪(近)。 如果您點選下面的按鈕,RNNoise將在瀏覽器中執行Javascript中的噪聲抑制。 該演算法實時執行,但我們有意延遲幾秒鐘,以便更容易聽到去噪輸出。 確保戴耳機,否則您會聽到反饋迴路。 要開始演示,請選擇“無抑制”或“RNNoise”。 您可以在兩者之間切換以檢視抑制的效果。 如果您的輸入沒有足夠的噪音,您可以通過點選“白噪聲”按鈕人工新增。
把你的噪音捐給科學


如果你認為這項工作是有用的,那麼有一個簡單的方法來幫助它更好的完成!所需要的只是一分鐘的時間。點選下面的連結,讓我們從你所在的地方記錄一分鐘的噪音。該噪聲可用於改善神經網路的訓練。作為一個副作用,這意味著當您使用它進行視訊會議(例如WebRTC)時,網路將會知道您有什麼樣的噪音,並可能會做得更好。我們對任何可以使用語音進行通訊的環境感興趣。這可以是你的辦公室,你的車,在街上,或任何你可以使用你的手機或電腦的地方。


捐一分鐘的噪音!


從哪裡來
如果您想更多地瞭解RNNoise的技術細節,請參閱本文(尚未提交)。該程式碼仍然在積極的開發(沒有凍結的API),但已經在應用程式中可用。它目前的目標是VoIP /視訊會議應用程式,但通過一些調整,它可能適用於許多其他任務。一個明顯的目標是自動語音識別(ASR),雖然我們只能去噪嘈雜的語音並將輸出傳送到ASR,但這是次優的,因為它丟棄了有關過程的固有不確定性的有用資訊。當ASR不僅知道最可能幹淨的講話,而且還可以依賴於這一估計值時,這是更有用的。 RNNoise的另一個可能的“重新定位”是為電動樂器創造一個更加智慧的噪音門。所有它應該採取的是良好的訓練資料和一些程式碼的變化,將一個Raspberry Pi變成一個真正好的吉他噪音門。任何人我們還沒有考慮過許多​​其他潛在的應用程式。


如果您想對此演示進行評論,可以在這裡進行。


-Jean-Marc Valin([email protected])2017年9月27日
其他資源
程式碼:RNNoise Git倉庫(Github映象)
J.-M。 Valin,A Hybrid DSP / Deep Learning Approach to Real-time Full-Band Speech Enhancement,arXiv:1709.08243 [cs.SD],2017。
讓 - 馬克的博文發表評論
致謝
特別感謝Michael Bebenita,Thomas Daede和Yury Delendik的幫助。感謝Reuben Morais對Keras的幫助。