2017-03-04 93 views
0

我有已經處理擲圖像:OpenCV的墊圖像數據結構

//UIImage to Mat 
cv::Mat originalMat = [self cvMatFromUIImage:inputImage]; 

//Grayscale 
cv::Mat grayMat; 
cv::cvtColor(originalMat, grayMat, CV_RGB2GRAY); 

//Blur 
cv::Mat gaussMat; 
cv::GaussianBlur(grayMat , gaussMat, cv::Size(9, 9), 2, 2); 

//Threshold 
cv::threshold(grayMat,tMat,100,255,cv::THRESH_BINARY); 

比我想分析(計算的白點和黑點數量)該初級講座到線。例如:我有一張圖像100x120px,我想查看x = 5y = from 0 to 119;反之亦然x = 0..99; y = 5;

所以我期望Mat將包含x - Mat.colsy - Mat.rows但看起來它以另一種方式保存數據。比如我試圖改變像素的顏色,初級講座到線,但沒有得到2線:

for(int x = 0; x < tMat.cols; x++){ 
    tMat.at<cv::Vec4b>(5,x)[0] = 100; 
} 

for(int y = 0; y < tMat.rows; y++){ 
    tMat.at<cv::Vec4b>(y,5)[0] = 100; 
} 
return [self UIImageFromCVMat:tMat]; 

結果爲黑白圖像:

enter image description here

我爲什麼我以前不得到2行呢?是否可以直接在Mat中繪製\ check lines?如果我要檢查通過y = kx + b計算的線路,該怎麼辦?

回答

3

您正在以錯誤的方式訪問像素值。你與形象,只有一個通道工作,這就是爲什麼你要訪問這樣的像素值:

for (int x = 0; x < tMat.cols; x++){ 
    tMat.at<unsigned char>(5, x) = 100; 
} 

for (int y = 0; y < tMat.rows; y++){ 
    tMat.at<unsigned char>(y, 5) = 100; 
} 

墊子元素的類型是由兩個屬性定義 - 在通道數和底層數據類型。如果您不知道這些術語的含義,我強烈建議您閱讀方法cv::Mat::type(),cv::Mat::channels()cv::Mat::depth()的文檔。

兩個例子:

mat.at<float>(x, y) = 1.0f; // if mat type is CV_32FC1 
mat.at<cv::Vec3b>(x, y) = Vec3b(1, 2, 3); // if mat type is CV_8UC3 
2

可能是Mat數據類型的問題。閾值的輸出是8位或32位的單通道圖像(http://docs.opencv.org/2.4/modules/imgproc/doc/miscellaneous_transformations.html?highlight=threshold#threshold),所以您可能不應該使用Mat.at<Vec4b>[0]來設置值。

下面是返回矩陣類型的函數。用法在註釋部分。從How to find out what type of a Mat object is with Mat::type() in OpenCV複製。

std::string type2str(int type){ 
//string ty = type2str(comparisonResult.type()); 
//printf("Matrix: %s %dx%d \n", ty.c_str(), comparisonResult.cols, comparisonResult.rows); 

string r; 

uchar depth = type & CV_MAT_DEPTH_MASK; 
uchar chans = 1 + (type >> CV_CN_SHIFT); 

switch (depth) { 
case CV_8U: r = "8U"; break; 
case CV_8S: r = "8S"; break; 
case CV_16U: r = "16U"; break; 
case CV_16S: r = "16S"; break; 
case CV_32S: r = "32S"; break; 
case CV_32F: r = "32F"; break; 
case CV_64F: r = "64F"; break; 
default:  r = "User"; break; 
} 

r += "C"; 
r += (chans+'0'); 

return r;}