EmguCV從位圖(Bitmap)加載Image 速度慢的問題


  先說背景。最近在用C#+EmguCV(其實就是用P/Invoke封閉了OpecCV,與OpenCVDotNet差不多) 做一個視頻的東西。視頻是由攝像頭采集回來的1f/s,2048X1000大小,其實是由一張張位圖(Bitmap)未經壓縮制成的avi視頻文件,而且圖像很不清楚。在GSpot可以看出視頻是BI_RGB Raw Bitmap編碼,所以我用EmguCV里的Capture(string filename)(即cvCaptureFromFile(string filename))這個函數從文件打不開Capture(幾乎所有編碼器都裝了但還是打不開,如果有人知道怎么打開請賜教,那就沒有下文的內容了,非常感謝),於是不得不用其它方法。我的做法是用Windows API函數的AVI File Functions這一系列函數(在AVIFIL32.dll里)打開,然后得到一幀一幀的數據流,最后把它轉化成Bitmap。當然,這中間用到了P/Invoke封閉這些函數。

  但是可氣的是EmguCV里所有的操作都是針對他自己的封閉類型Image<TColor,TDepth>來操作的,由於我的是8位單通道灰度圖像即Image<Gray,byte>。辦法有:

  (一)顯然,最簡單的辦法就是用Image<Gray,byte>(Bitmap bmp)這個構造函數來構造Image<Gray,byte>。但是在運行過程中發現圖像加載非常的慢慢,最先還以為是圖像預處理比如高斯平滑濾波、腐蝕等造成的,可是當我用Stopwatch查看才發現Image<Gray,byte>(Bitmap bmp)這個構造函數來構造Image<Gray,byte>這個過程就花了6-8秒,這是肯定不能接受的。

  (二)在查看了EmguCV的源代碼后我又使用了Image.Bitmap函數來直接set位圖,但是這一步仍然要花6-8秒。

  (三)后來想用不安全代碼將位圖的數據直接轉化成Image<Gray,byte>,我寫了半天,仍然沒有成功,(要是哪個知道也請告知)

  (四)因為后來發現Image<Gray,byte>的構造函數中有從文件中直接加載這一項,試過后發現這一過程很快,於是有了這個方法。

    1.從avi中得到位圖

    2.將位圖保存為臨時文件,考慮其它因素,文件放在了用戶臨時文件夾

    3.將2中保存的位圖文件加載到Image<Gray,byte>中

    4.刪除位圖臨時文件

最后運行的結果是:以上四步在0.2-0.3秒左右。順利到達要求。

 1 //得到指定幀的位圖,這個是自定義函數
 2 _bmpCurrentBMP = _aviFile.GetFrameAsBitmap(index);  3 try
 4 {  5   //用以下方法只用時間0.2s左右  6   //保存位圖於臨時文件夾
 7    _bmpCurrentBMP.Save(_ImageTempFileName);  8   //從文件中加載位圖
 9    _pCurrentImageRGB = new Image<Bgr, byte>(_ImageTempFileName); 10   //刪除位圖
11   File.Delete(_ImageTempFileName); 12  } 13  catch (IOException ex) 14  { 15    MessageBox.Show(ex.Message); 16    return; 17 }


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM