OpenCV: trouver toutes les coordonnées non nulles d'une image Mat binaire

j'essaie de trouver les coordonnées non-zéro (x,y) d'une image binaire.

j'ai trouvé quelques références à la fonction countNonZero() qui ne compte que les coordonnées non nulles et findNonZero() que je ne sais pas comment accéder ou utiliser puisqu'il semble avoir été complètement retiré de la documentation.

est la référence la plus proche que j'ai trouvée, mais toujours pas utile du tout. J'apprécierais toute aide spécifique.

Modifier: - Spécifier, c'est à l'aide de C++

17
demandé sur Community 2013-10-08 12:25:08

3 réponses

Ici explique comment findNonZero() sauve des éléments non-zéros. Les codes suivants devraient être utiles pour accéder aux coordonnées non-zéro de votre binaire image. Méthode 1 utilisée findNonZero() dans OpenCV, et la méthode 2 a vérifié chaque pixel pour trouver les non-zéros (positifs).

Méthode 1:

#include <iostream>
#include <opencv2/core/core.hpp>
#include <opencv2/highgui/highgui.hpp>
using namespace std;
using namespace cv;

int main(int argc, char** argv) {
    Mat img = imread("binary image");
    Mat nonZeroCoordinates;
    findNonZero(img, nonZeroCoordinates);
    for (int i = 0; i < nonZeroCoordinates.total(); i++ ) {
        cout << "Zero#" << i << ": " << nonZeroCoordinates.at<Point>(i).x << ", " << nonZeroCoordinates.at<Point>(i).y << endl;
    }
    return 0;
}

Méthode 2:

#include <iostream>
#include <opencv2/core/core.hpp>
#include <opencv2/imgproc/imgproc.hpp>
#include <opencv2/highgui/highgui.hpp>
using namespace std;
using namespace cv;

int main(int argc, char** argv) {
    Mat img = imread("binary image");
    for (int i = 0; i < img.cols; i++ ) {
        for (int j = 0; j < img.rows; j++) {
            if (img.at<uchar>(j, i) > 0) {  
                cout << i << ", " << j << endl;     // Do your operations
            }
        }
    }
    return 0;
}
31
répondu WangYudong 2017-09-21 10:45:21

il y a le code source suivant qui était fourni pour OpenCV 2.4.3, qui peut être utile:

#include <opencv2/core/core.hpp>
#include <vector>

/*! @brief find non-zero elements in a Matrix
 *
 * Given a binary matrix (likely returned from a comparison
 * operation such as compare(), >, ==, etc, return all of
 * the non-zero indices as a std::vector<cv::Point> (x,y)
 *
 * This function aims to replicate the functionality of
 * Matlab's command of the same name
 *
 * Example:
 * \code
 *  // find the edges in an image
 *  Mat edges, thresh;
 *  sobel(image, edges);
 *  // theshold the edges
 *  thresh = edges > 0.1;
 *  // find the non-zero components so we can do something useful with them later
 *  vector<Point> idx;
 *  find(thresh, idx);
 * \endcode
 *
 * @param binary the input image (type CV_8UC1)
 * @param idx the output vector of Points corresponding to non-zero indices in the input
 */
void find(const cv::Mat& binary, std::vector<cv::Point> &idx) {

    assert(binary.cols > 0 && binary.rows > 0 && binary.channels() == 1 && binary.depth() == CV_8U);
    const int M = binary.rows;
    const int N = binary.cols;
    for (int m = 0; m < M; ++m) {
        const char* bin_ptr = binary.ptr<char>(m);
        for (int n = 0; n < N; ++n) {
            if (bin_ptr[n] > 0) idx.push_back(cv::Point(n,m));
        }
    }
}

Note - il semble que la signature de la fonction était fausse donc j'ai changé la sortie vector passer par référence.

5
répondu Roger Rowland 2013-10-08 11:19:17

Vous pouvez le trouver sans utiliser findNonZero() cette méthode opencv. plutôt u peut l'obtenir en utilisant simplement 2 pour les boucles. voici l'extrait de code. j'espère que ça peut aider à u.

**

for(int i = 0 ;i <image.rows() ; i++){// image : the binary image
            for(int j = 0; j< image.cols() ; j++){
                double[] returned = image.get(i,j); 
                int value = (int) returned[0]; 
                if(value==255){
                System.out.println("x: " +i + "\ty: "+j);// returned the (x,y) //co ordinates of all white pixels.
                }
            }

        }

**

-2
répondu Tanusree 2016-07-05 05:25:51