2013-01-08 78 views
2

嗨我正在從事計算機視覺項目,並試圖從相機使用openCV/C++檢測平方。我已經從openCV庫下載源代碼,但它似乎很難失去fps。有誰知道如何解決這個問題?有一個關於我的下面的測試視頻鏈接,檢查出來: http://magicbookproject.blogspot.co.uk/2012/12/detect-paper-demo.html檢測廣場opencv和c + +

下面是代碼,只是發現了另一篇文章:

void find_squares(Mat& image, vector<vector<Point> >& squares) 
{ 
// blur will enhance edge detection 
Mat blurred(image); 
medianBlur(image, blurred, 9); 

Mat gray0(blurred.size(), CV_8U), gray; 
vector<vector<Point> > contours; 

// find squares in every color plane of the image 
for (int c = 0; c < 3; c++) 
{ 
    int ch[] = {c, 0}; 
    mixChannels(&blurred, 1, &gray0, 1, ch, 1); 

    // try several threshold levels 
    const int threshold_level = 2; 
    for (int l = 0; l < threshold_level; l++) 
    { 
     // Use Canny instead of zero threshold level! 
     // Canny helps to catch squares with gradient shading 
     if (l == 0) 
     { 
      Canny(gray0, gray, 10, 20, 3); // 

      // Dilate helps to remove potential holes between edge segments 
      dilate(gray, gray, Mat(), Point(-1,-1)); 
     } 
     else 
     { 
       gray = gray0 >= (l+1) * 255/threshold_level; 
     } 

     // Find contours and store them in a list 
     findContours(gray, contours, CV_RETR_LIST, CV_CHAIN_APPROX_SIMPLE); 

     // Test contours 
     vector<Point> approx; 
     for (size_t i = 0; i < contours.size(); i++) 
     { 
       // approximate contour with accuracy proportional 
       // to the contour perimeter 
       approxPolyDP(Mat(contours[i]), approx, arcLength(Mat(contours[i]), true)*0.02, true); 

       // Note: absolute value of an area is used because 
       // area may be positive or negative - in accordance with the 
       // contour orientation 
       if (approx.size() == 4 && 
         fabs(contourArea(Mat(approx))) > 1000 && 
         isContourConvex(Mat(approx))) 
       { 
         double maxCosine = 0; 

         for (int j = 2; j < 5; j++) 
         { 
           double cosine = fabs(angle(approx[j%4], approx[j-2], approx[j-1])); 
           maxCosine = MAX(maxCosine, cosine); 
         } 

         if (maxCosine < 0.3) 
           squares.push_back(approx); 
       } 
     } 
    } 
} 

}

+0

你能告訴我們一些代碼...你是否從源代碼提供的方塊樣本工作? – foundry

+0

這裏有任何建議嗎?我知道它的形象,如何改變它一點點,然後它將適用於相機。 – user1959079

回答

3

你可以,如果你加快步伐不介意失去準確性。例如

// find squares in every color plane of the image 
for (int c = 0; c < 3; c++) 

您正在循環三個顏色平面。只需檢查一種顏色(就像圖像是灰度一樣),這應該是速度的三倍。

也嘗試沒有Canny,這是很慢。設置一個use_canny參數,

if (l == 0 && use_canny) 
    { 
     Canny(gray0, gray, 10, 20, 3); // 

比較有無。我得到了可接受的結果,速度相當快。

+0

感謝您的回覆。你說沒有Canny嘗試,那麼如何做邊緣檢測呢? – user1959079

+0

@ user1959079這不是絕對必要的。在輪廓提取階段之前,您可以通過簡單的閾值得到足夠好的結果。 –

+0

@ user1959079看到我的更新,只是嘗試沒有Canny,它爲我工作。還有其他的參數可以調整來補償 – foundry

1

計算機視覺的一個很好的經驗法則是在進行任何密集處理之前將圖像轉換爲灰度。只有在發現絕對必要時才通過顏色通道循環。我建議如下圖案爲對象識別:

  1. 轉換圖像爲灰度
  2. 過濾的灰度圖像,以更簡單的格式(精明,閾值,邊沿檢測)
  3. 執行重處理(檢測正方形形狀)
  4. 重建原始圖像與處理後的值(畫/存儲您的方塊)

記住,你正在做的所有這些步驟對每一幀畫面,所以一定要消除任何你網絡nd是不必要的。由於這些代碼會經常運行,因此即使進行了一些小的優化,您也會看到巨大的性能優勢,所以值得花一些時間進行優化。

+0

感謝您的回覆。我的問題是從相機而不是圖像檢測正方形。 – user1959079

+0

就OpenCV而言,相機輸入只是一系列單獨的圖像。圖像來自實時​​相機而不是視頻文件或圖像目錄的事實是無關緊要的。 – Jestin