[演算法] Huffman Coding

Chacha
Oct 12, 2023

--

連假結束啦,不知道大家連假都過得如何🏞 不論過得有多精彩,還是要收心回來讓我們繼續學習啦😊

這次要來繼續往下前進,介紹演算法。是不是看到這裡很奇怪,怎麼突然又回去說演算法了,不用擔心,實際上我們只是先停下腳步先學習資料結構,等我們站穩腳步後再回過頭繼續學習演算法,因為我們接下來要學習的會使用到之前所學的資料結構,就讓我們繼續看下去

Huffman Coding

Huffman Coding(霍夫曼編碼)在電腦資料處理中,使用變長編碼表對源符號(如檔案中的一個字母)進行編碼,其中變長編碼表是通過一種評估來源符號出現機率的方法得到的,出現機率高的字母使用較短的編碼,反之出現機率低的則使用較長的編碼,這便使編碼之後的字串的平均長度、期望值降低,從而達到無失真壓縮數據的目的[1]。

從上述應該相當難看出來到底 Huffman Coding 在做什麼,沒關西就讓我來解釋一下。

首先上述有提到會將出現的資料(這裡用英文字母做舉例)做成編碼表,邊碼表以資料已出現的次數做編排,將最常出現的字母用較少的空間儲存,反之將使用較少的字母用較多的空間儲存,減少整體的儲存空間

第二就是這是一種無失真的壓縮技術,因為以上述方式來儲存資料,我們並不是以丟掉資料來達成減少儲存空間,因此是相當不錯的資料壓縮演算法,那接下來就讓我一步一步來操作 Huffman Coding 吧

既然要將資料解壓縮那就勢必要有一筆資料,在這裡我們嘗試將資料 AAAA BB CCCD 這筆資料做壓縮吧。

在壓縮前我們必須先知道原本的儲存空間為多少,這樣才可以做比較因此我們先來定義一下每個字母的儲存空間,且因為是電腦資料處理,所已將儲存空間以二位元的方式顯示給大家看如下

A = 000
B = 001
C = 010
D = 011
SPACE = 100
AAAABB CCCD => 000000000000001001100010010010011 //33 bits

我們知道原始資料之後就開始第一步,首先我們要製作編碼表,那要如何製作呢?這裡我們就要將資料轉換成 Huffman Tree(霍夫曼樹),才能將資料轉換成編碼表。

如同一開始所介紹,我們要先統計資料出現的頻率,A 出現4次、B 出現2次、C 出現3次、D 出現1次、SPACE 出現1次,在了解出現頻率後就要來建立 Huffman Tree,我們先將資料出現最少的2項取出,分別為 D 與 SPACE,成為最底下的葉節點,並將其出現次數相加成為其父節點,再將資料加入回原本資料裡成為新的資料,之後繼續重複上述步驟,將出現頻率最少的兩資料做結合,直至完成所有資料的整理,這就是個完整的 Huffman Tree。

在得到完整的 Huffman Tree 之後我們將其樹的左鏈結設定為 0 ,右鏈結設定為 1,然後從根結點向下走至該資料的節點會經過的數字記錄下,並做成表格就完成我們的編碼表了,是不是聽起來相當複雜呢,沒關係請搭配我以下的圖片及上述文字再消化一下

huffman tree

是否有更好理解呢?所以最終我們會得到的編碼表以及資料轉換後的大小就會如下

A = 0
B = 111
C = 10
D = 1100
SPACE = 1101
AAAABB CCCD => 0000011111111011010101100 //25 bits

從上述來看經過壓縮之後資料的大小減少了 8 bits,雖然看起來很少,但若以比例來看的話已經減少了 25 %,若之後使用的資料量變大就可以知道其好出了。

在大部分情況下我們使用 Huffman Coding 會是相當不錯的選擇,當然也會有遇到最壞情況,此時就必須對資料做一些調整,但目前這不再我的探討範圍,所以目前就不多做討論,另外還有一點要注意的是每次在做 Huffman Coding 壓縮或解碼時都要遵守其編碼表,因為即使是相同的資料,再做成 Huffman Tree 時都有可能不相同,可能因為最小值的有重複因而選擇不同或是資料在葉節點的擺放都會影響到其編碼表,這點是在使用上須特別注意的。

在這次學習時才終於知道為甚麼要突然跳到學習資料結構,因為還有很多方法及工具是需要這些基礎的。

在學習的過程中我也相當感興趣,畢竟這是我從沒碰過且相當直觀的概念,概念上可能在剛開始學習時不太懂,一旦搭配圖片時整個人就豁然開朗起來,原來是這麼回事的感覺🧐之後都一路順暢,並且身心靈會感到相當舒暢,希望往後學習也能保持,那我們下篇文章見啦✋

--

--

Chacha

我是迷惘程式小菜鳥,多看多聽多學,在透過將知識輸出後加深印象,希望能在知識之間的交流及碰撞後不斷成長茁壯,這些學習心得都是我透過自身學習後的分享,許多圖片也是我親手製作,雖然不夠美觀,但希望也能幫助其他人能更加理解文章內容,心得內容有誤也相當歡迎批評及指教