HEVC/H265 HM10.0 分析(三)TAppDecTop.cpp

在TAppDecTop.cpp? ,最重要的是decode 函數,下面將對其進行分析,是解碼上層的一個重要函數。

代碼如下,代碼后將進行分析。

Void TAppDecTop::decode()
{Int                 poc;TComList<TComPic*>* pcListPic = NULL;ifstream bitstreamFile(m_pchBitstreamFile, ifstream::in | ifstream::binary);if (!bitstreamFile){fprintf(stderr, "\nfailed to open bitstream file `%s' for reading\n", m_pchBitstreamFile);exit(EXIT_FAILURE);}InputByteStream bytestream(bitstreamFile);// create & initialize internal classesxCreateDecLib();xInitDecLib  ();m_iPOCLastDisplay += m_iSkipFrame;      // set the last displayed POC correctly for skip forward.// main decoder loopBool recon_opened = false; // reconstruction file not yet opened. (must be performed after SPS is seen)while (!!bitstreamFile){/* location serves to work around a design fault in the decoder, whereby* the process of reading a new slice that is the first slice of a new frame* requires the TDecTop::decode() method to be called again with the same* nal unit. */streampos location = bitstreamFile.tellg();AnnexBStats stats = AnnexBStats();Bool bPreviousPictureDecoded = false;vector<uint8_t> nalUnit;InputNALUnit nalu;byteStreamNALUnit(bytestream, nalUnit, stats);// call actual decoding functionBool bNewPicture = false;if (nalUnit.empty()){/* this can happen if the following occur:*  - empty input file*  - two back-to-back start_code_prefixes*  - start_code_prefix immediately followed by EOF*/fprintf(stderr, "Warning: Attempt to decode an empty NAL unit\n");}else{read(nalu, nalUnit);if( (m_iMaxTemporalLayer >= 0 && nalu.m_temporalId > m_iMaxTemporalLayer) || !isNaluWithinTargetDecLayerIdSet(&nalu)  ){if(bPreviousPictureDecoded){bNewPicture = true;bPreviousPictureDecoded = false;}else{bNewPicture = false;}}else{bNewPicture = m_cTDecTop.decode(nalu, m_iSkipFrame, m_iPOCLastDisplay);if (bNewPicture){bitstreamFile.clear();/* location points to the current nalunit payload[1] due to the* need for the annexB parser to read three extra bytes.* [1] except for the first NAL unit in the file*     (but bNewPicture doesn't happen then) */bitstreamFile.seekg(location-streamoff(3));bytestream.reset();}bPreviousPictureDecoded = true; }}if (bNewPicture || !bitstreamFile){m_cTDecTop.executeLoopFilters(poc, pcListPic);printf("\npoc =%d\n",poc);}if( pcListPic ){printf("\nnaluType =%d\n",nalu.m_nalUnitType);if ( m_pchReconFile && !recon_opened ){if (!m_outputBitDepthY) { m_outputBitDepthY = g_bitDepthY; }if (!m_outputBitDepthC) { m_outputBitDepthC = g_bitDepthC; }m_cTVideoIOYuvReconFile.open( m_pchReconFile, true, m_outputBitDepthY, m_outputBitDepthC, g_bitDepthY, g_bitDepthC ); // write moderecon_opened = true;}if ( bNewPicture && (   nalu.m_nalUnitType == NAL_UNIT_CODED_SLICE_IDR|| nalu.m_nalUnitType == NAL_UNIT_CODED_SLICE_IDR_N_LP|| nalu.m_nalUnitType == NAL_UNIT_CODED_SLICE_BLA_N_LP|| nalu.m_nalUnitType == NAL_UNIT_CODED_SLICE_BLANT|| nalu.m_nalUnitType == NAL_UNIT_CODED_SLICE_BLA ) ){xFlushOutput( pcListPic );}// write reconstruction to fileif(bNewPicture){xWriteOutput( pcListPic, nalu.m_temporalId );}}}xFlushOutput( pcListPic );// delete buffersm_cTDecTop.deletePicBuffer();// destroy internal classesxDestroyDecLib();
}



代碼xCreateDecLib 和 xInitDecLib 重要是初始化四叉樹和解碼需要的全局變量和申請內存。

當提供一個碼流文件的文件名后,進行ifstream bitstreamFile(m_pchBitstreamFile, ifstream::in | ifstream::binary); 以二進制方式打開文件名,碼流以字節方式InputByteStream bytestream(bitstreamFile);進行讀操作。


我們都知道,HEVC/H265 是以NAL方式組織數據的,解析VPS,SPS,PPS,SEI,SEI_SUFFIX 后,其他的是一個個slice的NAL數據,而Deblocking & SAO Filters 等濾波是對整個picuture進行濾波操作,出現從第二幀開始,每幀的第一個slice兩次進行解析,這是參考軟件的一個bug或不好的地方,其實完全可以知道是否是最后一個slice,不必進行兩次打開。

所以出現:

bitstreamFile.clear();

bitstreamFile.seekg(location-streamoff(3));
bytestream.reset();


大家有興趣,可以先增加一個變量,判斷是否是最后一個slice,就不需要執行上面代碼了。


如下代碼是從來不會執行,因為HEVC/H265沒有cavlc,也就不會有slice part A ,slice part B,slice part C ,是現實的編解碼告訴了設計者,slice part A ,slice part B,slice part C 沒有人使用,就被拋棄了,實際的編解碼從來沒有實現slice part A ,slice part B,slice part C 等編解碼的。

?if( (m_iMaxTemporalLayer >= 0 && nalu.m_temporalId > m_iMaxTemporalLayer) || !isNaluWithinTargetDecLayerIdSet(&nalu)? )
????? {
??????? if(bPreviousPictureDecoded)
??????? {
????????? bNewPicture = true;
????????? bPreviousPictureDecoded = false;
??????? }
??????? else
??????? {
????????? bNewPicture = false;
??????? }
????? }


解碼和濾波后當然就是輸出重構數據,xWriteOutput( pcListPic, nalu.m_temporalId ), 如果slice是NAL_UNIT_CODED_SLICE_IDR,NAL_UNIT_CODED_SLICE_IDR_N_LP,NAL_UNIT_CODED_SLICE_BLA_N_LP,NAL_UNIT_CODED_SLICE_BLANT,NAL_UNIT_CODED_SLICE_BLA中的一種,將解碼產生的picture全部清空,沒有任何參考幀,相當于一個新的sequence進行解碼了。


其他的代碼很簡單,請自己分析。





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

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

相關文章

windows下xmllib2使用簡介 64位

1&#xff1a;環境配置 包含目錄下 包含include libxml2_64\include     包含xmllib庫路徑  libxml2_64 注意 libxml分為32位程序和64位程序&#xff0c;這兩種的環境需要的lib不一樣&#xff0c;需要分別下載 需要使用庫 libxml2.lib 注意&#xff1a…

backtrader2

backtrader的基本策略構成&#xff1a; #構成 #Backtrader 回測代碼編寫流程如下&#xff1a; import backtrader as bt # 導入 Backtrader import backtrader.indicators as btind # 導入策略分析模塊 import backtrader.feeds as btfeeds # 導入數據模塊# 創建策略 class T…

解決瀏覽器 Provisional headers are shown 無法向后臺發送請求問題

前些天發現了一個巨牛的人工智能學習網站&#xff0c;通俗易懂&#xff0c;風趣幽默&#xff0c;忍不住分享一下給大家。點擊跳轉到教程。 我的情況和下面情況一樣&#xff0c;有一個斷點。 今天調試項目BUG&#xff0c;頁面的一個按鈕點擊后頁面無反應&#xff0c;去后臺找對…

臺灣郵政歷史常設展重新開幕

1月29日&#xff0c;重新開幕的臺灣郵政歷史常設展增加了與觀眾的對話和互動&#xff0c;希望吸引不同年齡層觀眾。中新社記者 孔任遠 攝 1月29日&#xff0c;重新開幕的臺灣郵政歷史常設展增加了與觀眾的對話和互動&#xff0c;希望吸引不同年齡層觀眾。中新社記者 孔任遠 攝 …

如何用vc6編譯ffmpeg, 并單步調試。

如何用vc6編譯ffmpeg, 并單步調試。目前官方ffmpeg的最新版本為0.9, 我們就以此為例&#xff1a; 1. 下載最新git版本的源代碼(http://ffmpeg.zeranoe.com/builds/, 本例下載的是2011-12-12版本) 2. 放到MSYS環境里配置&#xff0c;生成config.h文件。mingw gcc是能順利編譯…

backtrader指標

添加分析指標 # 添加分析指標 # 返回年初至年末的年度收益率 cerebro.addanalyzer(bt.analyzers.AnnualReturn, _name_AnnualReturn) # 計算最大回撤相關指標 cerebro.addanalyzer(bt.analyzers.DrawDown, _name_DrawDown) # 計算年化收益&#xff1a;日度收益 cerebro.addana…

Javascript DOM對屬性的操作

獲得屬性值 itnode . 屬性名稱          //只能操作w3c規定內容 itnode . getAttribute(屬性名稱)    //規定的 和 自定義的都可以獲取 設置屬性值 itnode . 屬性名稱 值        //只能操作w3c規定的屬性 itnode . setAttribute(名稱&#xff0c;值) …

172開頭的IP不一定是局域網的地址

前些天發現了一個巨牛的人工智能學習網站&#xff0c;通俗易懂&#xff0c;風趣幽默&#xff0c;忍不住分享一下給大家。點擊跳轉到教程。 A類 10.0.0.0-10.255.255.255 網絡數&#xff1a;1B類 172.16.0.0-172.31.255.255 網絡數&#xff1a;16C類 192.168.0.0-192.168.255.…

微信屏蔽百度紅包活動頁面,誰在焦慮?

1月29日消息&#xff0c;百度與中央電視臺合作的百度紅包鏈接分享頁面被微信屏蔽&#xff0c;打開相關頁面顯示&#xff1a;網頁包含誘導分享、關注等誘導行為內容&#xff0c;被多人投訴&#xff0c;為維護綠色上網環境&#xff0c;已經停止訪問該網頁。 雷鋒網了解到&#x…

Visual C++利用Intel C++ 編譯器提升多核性能與多媒體指令支持獲取更高的程序效率與縮小程序體積

Intel c編譯器有下列優點&#xff0c;建議VC項目開發采用intel c編譯器取代VS自帶c編譯器&#xff1a; 與 Microsoft Visual C 相兼容&#xff0c;可以嵌入 Microsoft Visual Studio 開發環境。 支持最新的多核處理器&#xff0c;并提供安全功能&#xff0c;可以通過執行堆棧…

Backtrader交易基礎

查看賬戶情況&#xff1a; class TestStrategy(bt.Strategy):def next(self):print(當前可用資金, self.broker.getcash())print(當前總資產, self.broker.getvalue())print(當前持倉量, self.broker.getposition(self.data).size)print(當前持倉成本, self.broker.getpositio…

IP地址分類/IP地址10開頭和172開頭和192開頭的區別

前些天發現了一個巨牛的人工智能學習網站&#xff0c;通俗易懂&#xff0c;風趣幽默&#xff0c;忍不住分享一下給大家。點擊跳轉到教程。 IP地址分類/IP地址10開頭和172開頭和192開頭的區別/判斷是否同一網段 簡單來說在公司或企業內部看到的就基本都是內網IP&#xff0c;AB…

Redis數據結構之簡單動態字符串SDS

Redis的底層數據結構非常多&#xff0c;其中包括SDS、ZipList、SkipList、LinkedList、HashTable、Intset等。如果你對Redis的理解還只停留在get、set的水平的話&#xff0c;是遠遠不足以應對面試提問的。本文簡單介紹了Redis底層最重要的數據結構 - 簡單動態字符串&#xff08…

Centos7 安裝OpenTSDB

Centos7 安裝OpenTSDB https://www.imzcy.cn/1697.html轉載于:https://www.cnblogs.com/RHadoop-Hive/p/10563385.html

職場潛規則冷思考:別讓老板“殺”了你

一位3年前共事過的同事走了&#xff0c;就在他以200多萬的房貸代價拿到大門鑰匙的時候&#xff0c;猝然倒在新房的樓梯上。另一個曾經在同一戰壕里沖鋒陷陣的同事被老板辭掉了&#xff0c;兢兢業業&#xff0c;起早貪黑&#xff0c;竟然沒有熬過35歲下崗這一關&#xff0c;這時…

Backtrader交易基礎2

成交價格確定&#xff1a; Order.Market 市價單&#xff0c;以當時市場價格成交的訂單&#xff0c;不需要自己設定價格。市價單能被快速達成交易&#xff0c;防止踏空&#xff0c;盡快止損/止盈&#xff1b; 按下一個 Bar &#xff08;即生成訂單的那個交易日的下一個交易日&…

windows 小技巧

2019獨角獸企業重金招聘Python工程師標準>>> 桌面圖標顯示不全、圖標呈現白色方塊 ie4uinit -show 關閉占用指定端口的進程 獲取進程: netstat -ano | findstr 端口號關閉進程&#xff1a;taskkill -f -pid 進程號文件被占用 打開任務管理器&#xff0c;切換到 性能…

進一步了解 apt-get 的幾個命令

前些天發現了一個巨牛的人工智能學習網站&#xff0c;通俗易懂&#xff0c;風趣幽默&#xff0c;忍不住分享一下給大家。點擊跳轉到教程。 用 apt-get 也很久了&#xff0c;沒多想它的實現&#xff0c;最近遇到 gstreamer 裝不上的問題&#xff0c;才多看看了它 apt-get 就是…

java學習筆記20(Arraylist復習,Collection接口方法,迭代器,增強型for循環)

集合&#xff1a;集合是Java提供的一種容器&#xff0c;可以用來存儲多個數據&#xff1b; 集合與數組的區別&#xff1a;集合的長度是可變的&#xff0c;數組的長度是固定的 集合中存儲的數據必須是引用類型數據&#xff1b; ArrayList回顧&#xff1a; public class Person {…

backtrader數據基礎

cerebro bt.Cerebro() cerebro.addstrategy(TestStrategy2) codes[600862.SH,300326.SZ,300394.SZ] #加載最近兩日交易數據 for code in codes:feed Addmoredata(dataname get_data(code,20200506),namecode)cerebro.adddata(feed) cerebro.run() 數據查看&#xff1a; cl…