简体   繁体   中英

Take elements that match from a pair of arrays (C++/OpenCV)

I'm using an OpenCV function that takes matching elements from two single channel matrices and gives you a resulting array with only that element. The function is called compare

cv::compare(maskMat, cv::GC_FGD, result, cv::CMP_EQ);

maskMat is my matrix containing any value from 0 , 1 , 2 , or 3 .

cv::GC_FGD is just a matrix with each element equal to 1.

cv::CMP_EQ is a flag that checks if the two elements are equal.

What I'd also like to take any values of cv::GC_PR_FGD , which is 3 . So basically, I wish I do something like (cv::GC_FGD || cv::GC_PR_FGD) , taking any element whose value is 1 or 3 for my new resulting matrix.

Is there a simple way to do this? Thanks

The compare function produces an output array with a value set to 255 if the corresponding comparison returns true .

What you could do is use a two-step process:
First, perform two individual comparisons to get two arrays with the respective true values. Second, combine the two matrices using a Matrix Expression :

cv::Mat result0;
cv::Mat result1;

cv::compare(maskMat, cv::GC_FGD,    result0, cv::CMP_EQ); // Compare for equality to 1.
cv::compare(maskMat, cv::GC_PR_FGD, result1, cv::CMP_EQ); // Compare for equality to 3.

cv::Mat result = cmp0 | cmp1; // Combine the result of the comparisons
                              // by using bit-wise OR.

The bit-wise OR is a matrix expression that calculates the output matrix by performing the bit-wise operation on the two input matrices. Since the two input matrices are just composed of 0 and 255 values, this effectively creates the output you desire.

You could also replace the compare function by the appropriate matrix expressions, which are just == :

cv::Mat cmp1 = maskMat == 1; // Compare for equality to 1.
cv::Mat cmp3 = maskMat == 3; // Compare for equality to 3.

cv::Mat result = max(cmp0, cmp1); // Combine the result of the comparisons
                                  // by using the max function.

The max function used above works equally as well as the bit-wise OR in this case.

Since matrix expressions can be arbitrarily combined, you could actually put it all on a single line:

cv::Mat result = (maskMat == 1) | (maskMat == 3);

Hope that helps!

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM