無損壓縮——Huffman編碼

最近項目中涉及到人臉關鍵點中神經網絡的壓縮,采用了性能較好的哈夫曼編碼進行。

源碼地址:https://github.com/believeszw/HuffmanCompress

1 引言

 哈夫曼(Huffman)編碼算法是基于二叉樹構建編碼壓縮結構的,它是數據壓縮中經典的一種算法。算法根據文本字符出現的頻率,重新對字符進行編碼。因為為了縮短編碼的長度,我們自然希望頻率越高的詞,編碼越短,這樣最終才能最大化壓縮存儲文本數據的空間。?
  假設現在我們要對下面這句歌詞“we will we will r u”進行壓縮。我們可以想象,如果是使用ASCII碼對這句話編碼結果則為:119 101 32 119 105 108 108 32 119 101 32 119 105 108 108 32 114 32 117(十進制表示)。我們可以看出需要19個字節,也就是至少需要152位的內存空間去存儲這些數據。?
  很顯然直接ASCII碼編碼是很浪費空間的,Unicode就更不用說了,下面我們先來統計一下這句話中每個字符出現的頻率。如下表,按頻率高低已排序:


2 哈夫曼二叉樹構建

2.1 初始隊列

  那么我們按出現頻率高低將其放入一個優先級隊列中,從左到右依次為頻率逐漸增加。

下面我們需要將這個隊列轉換成哈夫曼二叉樹,哈夫曼二叉樹是一顆帶權重的二叉樹,權重是由隊列中每個字符出現的次數所決定的。并且哈夫曼二叉樹始終保證權重越大的字符出現在越高的地方。

2.2 第一步合并

? ? ? ?首先我們從左到右進行合并,依次構建二叉樹。第一步取前兩個字符u和r來構造初始二叉樹,第一個字符作為左節點,第二個元素作為右節點,然后兩個元素相加作為新空元素,并且兩者權重相加作為新元素的權重。

 同理,新元素可以和字符i再合并,如下:

2.3 重新調整隊列

上圖新元素權重相加后結果是變大了,需要對權重進行重新排序。

然后再依次從左到右合并,每合并一次則進行一次隊列重新排序調整。如下:

經過多步操作之后,得到以下的哈夫曼二叉樹結構,也就是一個帶有權重的二叉樹:

2.4 哈夫曼編碼

有了上面帶權重的二叉樹之后,我們就可以進行編碼了。我們把二叉樹分支中左邊的支路編碼為0,右邊分支表示為1,如下圖:

這樣依次遍歷這顆二叉樹就可以獲取得到所有字符的編碼了。例如:‘ ’的編碼為10,‘l’的編碼為00,‘u’的編碼為11100等等。經過這個編碼設置之后我們可以發現,出現頻率越高的字符越會在上層,這樣它的編碼越短;出現頻率越低的字符越會在下層,編碼越短。經過這樣的設計,最終整個文本存儲空間才會最大化的縮減。?
  最終我們可以得到下面這張編碼表:

2.5 字符串編碼


  有了上面的編碼表之后,”we will we will r u”這句重新進行編碼就可以得到很大的壓縮,編碼表示為:01 110 10 01 1111 00 00 10 01 110 10 01 1111 00 00 10 11101 10 11100。這樣最終我們只需50位內存,比原ASCII碼表示節約了2/3空間,效果還是很理想的。當然現實中不是簡單這樣表示的,還需要考慮很多問題。

3 補充


  我們需要弄明白哈夫曼二叉樹概念,它是帶權路徑達到最小的二叉樹,也叫最優二叉樹。它不一定是完全二叉樹,也不一定是平衡二叉樹,它們描述的完全不是一件事情,完全沒有概念上的重疊關系。
?

?

?

?

?

?

?

?

?

?

?

?

?

?

?

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/448131.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/448131.shtml
英文地址,請注明出處:http://en.pswp.cn/news/448131.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

26條安全開車經驗 開車20年老司機分享

總有些人,覺得自己開車技術比舒馬赫牛叉,市區高速漂移無比瀟灑。也總有些人,覺得路是自家的鋪的,愛怎么開就怎么開,愛停哪就停哪,哪個不服打開車窗就是一句國罵一個中指。其實他們都沒有意識到,…

解決:Request header field Content-Type is not allowed by Access-Control-Allow-Headers

前些天發現了一個巨牛的人工智能學習網站,通俗易懂,風趣幽默,忍不住分享一下給大家。點擊跳轉到教程。 1. 前端 vue 工程 post 請求后端接口,報錯: Request header field Content-Type is not allowed by Access-Con…

書寫README的各種markdown語法

README 該文件用來測試和展示書寫README的各種markdown語法。GitHub的markdown語法在標準的markdown語法基礎上做了擴充,稱之為GitHub Flavored Markdown。簡稱GFM,GFM在GitHub上有廣泛應用,除了README文件外,issues和wiki均支持…

Apache2.4配置ssl

1》驗站 如下截圖,驗站就是在DNS域名商哪里,在對應host下面,添加一個TXT記錄類型,主機記錄,記錄值后,檢測即可。   2》SSL證書申請 阿里云,騰訊云有很多免費證書申請,免費的缺點是…

助你解決新手開車四大問題 為您支招

新手開車起步技巧涉及方方面面,對于新手來說,如何首次將車獨自開上路且不發生任何意外是眾多人熱切盼望的理想方式。但是新手上路難免會磕磕碰碰,發生小摩擦都是在所難免的,那么如何在起步階段就將發生事故的概率降到最低呢?在此…

VUE - get 、post 請求后端接口:get 、post 寫法 (Axios 中文說明文檔地址)

前些天發現了一個巨牛的人工智能學習網站,通俗易懂,風趣幽默,忍不住分享一下給大家。點擊跳轉到教程。 Axios 中文使用說明文檔地址:Axiox 中文說明文檔 我只是記錄下寫法,兩種請求都能正常運行: 1. 安裝…

C++11新特性——移動語義,右值引用

移動語義 有一些類的資源是__不可共享__的,這種類型的對象可以被移動但不能被拷貝,如:IO 或 unique_ptr 庫容器、string 和 shared_ptr 支持拷貝和移動,IO 和 unique_ptr 則只能移動不能拷貝。。 右值引用 右值引用是必須綁定到…

離合器半聯動點的判斷和技巧 為您支招

現在將離合器半聯動的使用方法揭密如下:將離合器抬到車開始動時你就別再抬了,你如果感覺到車有些快了,可再往下踩些,你如果感覺到車有些慢了,可再往起抬些,這樣可將車速控制在你想要的速度范圍之內。 ● 坡…

客戶端調用 WCF 的幾種方式

轉載網絡代碼.版權歸原作者所有.....客戶端調用&#xff37;&#xff23;&#xff26;的幾種常用的方式&#xff1a;&#xff11;普通調用var factory new DataContent.ServiceReference1.CustomerServiceClient();factory.Open();List<DataContent.ServiceReference1.Cust…

VUE:組件間相互跳轉、頁面帶參跳轉

前些天發現了一個巨牛的人工智能學習網站&#xff0c;通俗易懂&#xff0c;風趣幽默&#xff0c;忍不住分享一下給大家。點擊跳轉到教程。 只是記錄下用法&#xff1a; 從 A 頁面跳轉到 B 頁面。 如下寫法&#xff1a; A 頁面跳轉方式&#xff1a; 代碼&#xff1a; getdat…

Protocol Buffer 序列化

Protobuf使用 目錄 proto3的更新定義協議格式編譯protobufprotobuf_API 枚舉和嵌套類標準消息方法解析和序列化 寫一條消息閱讀消息編譯Protobuf擴展優化高級用法 proto3的更新 在第一行非空白非注釋行&#xff0c;必須寫&#xff1a; syntax "proto3";字段規…

如何調整反光鏡和座椅的位置 為您支招

【太平洋汽車網 學車頻道】首先要進行座椅的高度調整&#xff0c;上下調整座椅讓頭部離車頂至少還有一拳的距離。如果座椅調得太高&#xff0c;車輛在顛簸時頭部容易碰到車頂&#xff0c;調得太矮了又會影響視線。然后是前后距離的調整&#xff0c;當腳踩住制動踏板至最深處時…

關于hexo與github使用過程中的問題與筆記

快速閱讀 如何用github 和hexo 創建一個blog 1.github中要新建一個與用戶名同一樣的倉庫&#xff0c; 如:homehe.github.io - 必須是io后綴。一個帳戶 只能建立一個2. 綁定域名 &#xff0c; A記錄指向ip, cname記錄指向homehe.github.io 3. 配置sshkey - 個人設置 -> SSH a…

CSS 中 的 margin、border、padding 區別 (內邊距、外邊距)

前些天發現了一個巨牛的人工智能學習網站&#xff0c;通俗易懂&#xff0c;風趣幽默&#xff0c;忍不住分享一下給大家。點擊跳轉到教程。 圖解CSS padding、margin、border屬性 W3C組織建議把所有網頁上的對像都放在一個盒(box)中&#xff0c;設計師可以通過創建定義來控制這…

CMake 常用的預定義變量

CMake 常用的預定義變量 PROJECT_NAME : 通過 project() 指定項目名稱 PROJECT_SOURCE_DIR : 工程的根目錄 PROJECT_BINARY_DIR : 執行 cmake 命令的目錄 CMAKE_CURRENT_SOURCE_DIR : 當前 CMakeList.txt 文件所在的目錄 CMAKE_CURRENT_BINARY_DIR : 編譯目錄&#xff0c;…

什么是轉向燈?使用轉向燈有何技巧?

什么是轉向燈&#xff1f;如何使用轉向燈&#xff1f;新手司機對車輛還不是很熟悉&#xff0c;如何正確使用轉向燈&#xff0c;尤其是在不同路段中該怎么正確使用轉向燈&#xff0c;成為了很多新手們的困擾之一&#xff0c;今天我們就來為大家解決這個問題吧&#xff01; 轉向燈…

基于Flask開發企業級REST API應用(一)

關于我 編程界的一名小小程序猿&#xff0c;目前在一個創業團隊任team lead&#xff0c;技術棧涉及Android、Python、Java和Go&#xff0c;這個也是我們團隊的主要技術棧。 Github&#xff1a;github.com/hylinux1024 微信公眾號&#xff1a;angrycode 前面對Python WEB框架Fla…

解決:Do not use built-in or reserved HTML elements as component id: form

前些天發現了一個巨牛的人工智能學習網站&#xff0c;通俗易懂&#xff0c;風趣幽默&#xff0c;忍不住分享一下給大家。點擊跳轉到教程。 1. vue 新寫了個組件&#xff0c;運行工程成功&#xff0c;但界面沒有出效果&#xff0c;F12 提示有一個警告&#xff1a; Do not use …

移動語義,右值引用

移動語義 目錄 右值引用變量是左值move庫函數移動構造函數和移動賦值移動操作庫容器和異常移動賦值操作符移動后的對象必須是可以析構的合成移動操作右值移動左值拷貝右值在無法被移動時進行拷貝拷貝和交換賦值操作與移動移動迭代器右值引用和成員函數右值與左值引用的成員函…

集合練習:登錄注冊功能

需求&#xff1a; 1、登錄賬號唯一&#xff0c;在注冊時驗證輸入的賬號是否可用&#xff0c;若已存在&#xff0c;則不可用&#xff0c;若不存在則可用2、登錄時使用賬號密碼進行驗證1 /**2 * author Administrator3 * 登錄信息 4 */5 public class UserLogin {6 …