IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

OpenCV Discussion :

Problème d'exécution avec cvIntegral()


Sujet :

OpenCV

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Membre éclairé
    Avatar de betsprite
    Profil pro
    Inscrit en
    Avril 2010
    Messages
    472
    Détails du profil
    Informations personnelles :
    Âge : 37
    Localisation : France

    Informations forums :
    Inscription : Avril 2010
    Messages : 472
    Par défaut Problème d'exécution avec cvIntegral()
    Bonjour tout le monde,

    Je suis en train d'essayer d'utiliser la méthode cvIntegral de OpenCV pour obtenir la somme des valeurs des pixels d'une image.

    Seulement, je rencontre un problème avec OpenCV au moment de l'exécution, bien qu'il n'y ait aucune erreur

    Voici mon petit bout de code :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
     // Déclaration d'un pointeur sur IplImage :
        IplImage *image;
     
        // Chargement de l'image depuis un fichier :
        image = cvLoadImage("Images/test6.bmp");
     
        // Création d'une fenêtre dont la taille s'adapte à ce qu'elle contient :
        cvNamedWindow("Fenêtre", CV_WINDOW_AUTOSIZE);
     
        // Caractéristiques de l'image :
        int h = image->height;
        int w = image->width;
     
        // Déclaration de deux CvMat pour les calculs :
        CvMat* sum = cvCreateMat(h, w, CV_32F);
        CvMat* sqsum = cvCreateMat(h, w, CV_32F);
     
        // Calcul de sum et sqsum à partir de l'image :
        cvIntegral(image, sum, sqsum);
     
        // Résultats :
        cout << "***** SOMME *****";
        cout << endl;
     
        for(int y=0;y<10;y++)
        {
            for(int x=0;x<10;x++)
            {
                cout << cvmGet(sum, y, x);
            }
            cout << endl;
        }
     
    // ...
    Voici ci-dessous l'erreur que j'obtiens. Cependant, si je mets en commentaire la ligne avec l'utilisation de la méthode cvIntegral (ligne 94 sur le screen), le programme fonctionne ...

    Auriez-vous une idée ?

    Merci
    Images attachées Images attachées  

  2. #2
    Membre éprouvé
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Mars 2005
    Messages
    67
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 66
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : Développeur informatique

    Informations forums :
    Inscription : Mars 2005
    Messages : 67
    Par défaut
    Bonjour,

    Dans la doc ils disent :

    void cvIntegral( const CvArr* I, CvArr* S, CvArr* Sq=0, CvArr* T=0 );

    I
    The source image, w×h, single-channel, 8-bit, or floating-point (32f or 64f).
    S
    The sum image, w+1×h+1, single-channel, 32-bit integer or double precision floating-point (64f).
    Sq
    The square sum image, w+1×h+1, single-channel, double precision floating-point (64f).
    T
    The tilted sum image (sum of rotated by 45° image), w+1×h+1, single-channel, the same data type as sum.

    The function cvIntegral calculates one or more integral images for the source image as following:

    S(X,Y)=sumx<X,y<YI(x,y)

    Sq(X,Y)=sumx<X,y<YI(x,y)2

    T(X,Y)=sumy<Y,abs(x-X)<yI(x,y)

    After that the images are calculated, they can be used to calculate sums of pixels over an arbitrary rectangles, for example:

    sumx1<=x<x2,y1<=y<y2I(x,y)=S(x2,y2)-S(x1,y2)-S(x2,y1)+S(x1,x1)

    It makes possible to do a fast blurring or fast block correlation with variable window size etc.
    Donc :

    1 - Le "Images/test6.bmp" doit être en niveau de gris (je crois que par défaut opencv charge les images couleur sur 3 canaux)

    2 - il faut w+1 x h+1 pour la taille de sum et sqsum

    Cordialement

  3. #3
    Membre éclairé
    Avatar de betsprite
    Profil pro
    Inscrit en
    Avril 2010
    Messages
    472
    Détails du profil
    Informations personnelles :
    Âge : 37
    Localisation : France

    Informations forums :
    Inscription : Avril 2010
    Messages : 472
    Par défaut
    Tout d'abord, merci nihao pour ton aide

    Citation Envoyé par nihao
    2 - il faut w+1 x h+1 pour la taille de sum et sqsum
    Je ne comprends pas bien pourquoi la taille de sum et sqsum doit être plus grande que l'image

    Finalement, j'ai donc utilisé ceci :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    IplImage *image_nvg = cvCreateImage(cvGetSize(image), image->depth, 1);
    Afin d'être sûr d'avoir une image en niveaux de gris.

    Maintenant, mon code est le suivant :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    // Déclaration d'un pointeur sur IplImage :
        IplImage *image = cvLoadImage("Images/test6.bmp");
        IplImage *image_nvg = cvCreateImage(cvGetSize(image), image->depth, 1);
     
        // Création d'une fenêtre dont la taille s'adapte à ce qu'elle contient :
        cvNamedWindow("Fenêtre", CV_WINDOW_AUTOSIZE);
     
        // Caractéristiques de l'image :
        int h = image->height;
        int w = image->width;
     
        // Déclaration de deux CvMat pour les calculs :
        CvMat* sum = cvCreateMat(h+1, w+1, CV_32F);
        CvMat* sqsum = cvCreateMat(h+1, w+1, CV_32F);
     
        // Calcul de sum et sqsum à partir de l'image :
        cvIntegral(image_nvg, sum, sqsum);
     
        // Résultats :
        cout << "***** SOMME *****";
        cout << endl;
     
        for(int y=0;y<10;y++)
        {
            for(int x=0;x<10;x++)
            {
                cout << cvmGet(sum, y, x);
            }
            cout << endl;
        }
     
        // Affichage de l'image dans la fenêtre ci-dessus :
        cvShowImage("Fenêtre", image_nvg);
     
        // On attend que l'utilisateur appuie sur une touche :
        cvWaitKey(0);
     
        //Destruction de la fenêtre.
        cvDestroyWindow("Fenêtre");
     
        //Libération des IplImage :
        cvReleaseImage(&image);
        cvReleaseImage(&image_nvg);
     
        return 0;
    }
    Mais toujours le même problème

    D'autres idées ? Je continue pour ma part de chercher mais je ne vois pas vraiment d'où cela peut provenir..

    Merci!
    Images attachées Images attachées  

  4. #4
    Membre éprouvé
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Mars 2005
    Messages
    67
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 66
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : Développeur informatique

    Informations forums :
    Inscription : Mars 2005
    Messages : 67
    Par défaut
    Bonjour, ou plutot bonne nuit...
    Possible qu"il y ai un problème avec cvIntegral.
    Les routines de OpenSurf en ont besoin mais se serve d'une routine "maison"
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    /*********************************************************** 
    *  --- OpenSURF ---                                       *
    *  This library is distributed under the GNU GPL. Please   *
    *  use the contact form at http://www.chrisevansdev.com    *
    *  for more information.                                   *
    *                                                          *
    *  C. Evans, Research Into Robust Visual Features,         *
    *  MSc University of Bristol, 2008.                        *
    *                                                          *
    ************************************************************/
     
    #include "utils.h"
     
    #include "integral.h"
     
    //! Computes the integral image of image img.  Assumes source image to be a 
    //! 32-bit floating point.  Returns IplImage of 32-bit float form.
    IplImage *Integral(IplImage *source)
    {
      // convert the image to single channel 32f
      IplImage *img = getGray(source);
      IplImage *int_img = cvCreateImage(cvGetSize(img), IPL_DEPTH_32F, 1);
     
      // set up variables for data access
      int height = img->height;
      int width = img->width;
      int step = img->widthStep/sizeof(float);
      float *data   = (float *) img->imageData;  
      float *i_data = (float *) int_img->imageData;  
     
      // first row only
      float rs = 0.0f;
      for(int j=0; j<width; j++) 
      {
        rs += data[j]; 
        i_data[j] = rs;
      }
     
      // remaining cells are sum above and to the left
      for(int i=1; i<height; ++i) 
      {
        rs = 0.0f;
        for(int j=0; j<width; ++j) 
        {
          rs += data[i*step+j]; 
          i_data[i*step+j] = rs + i_data[(i-1)*step+j];
        }
      }
     
      // release the gray image
      cvReleaseImage(&img);
     
      // return the integral image
      return int_img;
    }
    (le getGray c'est cvCvtColor(imgsrc,imgdst,CV_BGR2GRAY))

    A voir...

  5. #5
    Membre éclairé
    Avatar de betsprite
    Profil pro
    Inscrit en
    Avril 2010
    Messages
    472
    Détails du profil
    Informations personnelles :
    Âge : 37
    Localisation : France

    Informations forums :
    Inscription : Avril 2010
    Messages : 472
    Par défaut
    Merci nihao pour ta réponse

    Citation Envoyé par nihao
    Possible qu"il y ai un problème avec cvIntegral.
    En fait, je voulais utiliser cvIntegral pour ne pas avoir à recoder la méthode de sommation des valeurs des pixels de l'image. La méthode en elle-même fonctionnait toutefois correctement mais seulement si la résolution de l'image était pas très grande. Je m'explique :

    Lorsque l'image avait une résolution strictement inférieure à 420x420, le programme fonctionnait correctement et j'avais le screen 1 (résolution 415x415 par exemple).

    Cependant, si la résolution dépassait 420x420 ou l'égalait, le programme ne fonctionnait plus à l'exécution (même s'il n'y avait aucune erreur à la compilation) et je me retrouvais avec le screen 2 (résolution 500x500 par exemple) (la fenêtre avec l'image s'ouvre tout en gris et se referme aussitôt donc impossible de la prendre en capture d'écran).

    Voici mon code avec la méthode de sommation qui semble retourner les bonnes valeurs quand le programme fonctionne (j'affiche les premières valeurs des cvMat pour vérifier dans le main, comme vous pouvez le voir sur le screen 1) et le main.

    Méthode sommation :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    void sommeImage(IplImage* image, int h, int w, CvMat* sum, CvMat* sqsum)
    {
        cvmSet(sum, 0, 0, cvGet2D(image, 0, 0).val[0]);
    	cvmSet(sqsum, 0, 0, cvGet2D(image, 0, 0).val[0]*cvGet2D(image, 0, 0).val[0]);
     
        // Remplissage de la première colonne :
    	for (int y=1;y<h;y++)
    	{
    	    cvmSet(sum, y, 0, cvGet2D(image, y, 0).val[0]+cvmGet(sum, y-1, 0));
            cvmSet(sqsum, y, 0, cvGet2D(image, y, 0).val[0]*cvGet2D(image, y, 0).val[0]+cvmGet(sqsum, y-1, 0));
    	}
     
        // Remplissage de la première ligne :
    	for (int x=1;x<w;x++)
    	{
    	    cvmSet(sum, 0, x, cvGet2D(image, 0, x).val[0]+cvmGet(sum, 0, x-1));
    		cvmSet(sqsum, 0, x, cvGet2D(image, 0, x).val[0] * cvGet2D(image, 0, x).val[0]+cvmGet(sqsum, 0, x-1));
    	}
     
        // Calcul sur les autres pixels :
    	for (int y=1;y<h;y++)
    	{
    		for (int x=1;x<w;x++)
    		{
    		    cvmSet(sum, y, x, cvGet2D(image, y, x).val[0]+cvmGet(sum, y, x-1)+cvmGet(sum, y-1, x)-cvmGet(sum, y-1, x-1));
                cvmSet(sqsum, y, x, cvGet2D(image, y, x).val[0]*cvGet2D(image, y, x).val[0]+cvmGet(sqsum, y, x-1)+cvmGet(sqsum, y-1, x)-cvmGet(sqsum, y-1, x-1));
            }
    	}
    }
    Main :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    int main()
    {
        // Déclaration d'un pointeur sur IplImage :
        IplImage *image = cvLoadImage("Images/test6.bmp");
            // IplImage *image_nvg = cvCreateImage(cvGetSize(image), image->depth, 1);
     
        // Création d'une fenêtre dont la taille s'adapte à ce qu'elle contient :
        cvNamedWindow("Fenêtre", CV_WINDOW_AUTOSIZE);
     
        // Caractéristiques de l'image :
        int h = image->height;
        int w = image->width;
     
        // Déclaration de deux CvMat pour les calculs :
        CvMat* sum = cvCreateMat(h, w, CV_32FC1);
        CvMat* sqsum = cvCreateMat(h, w, CV_32FC1);
     
        // Calcul de sum et sqsum à partir de l'image :
        sommeImage(image, h, w, sum, sqsum);
     
    // [...]
    Auriez-vous une idée ?

    Merci
    Images attachées Images attachées   

  6. #6
    Membre éprouvé
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Mars 2005
    Messages
    67
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 66
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : Développeur informatique

    Informations forums :
    Inscription : Mars 2005
    Messages : 67
    Par défaut
    Bonjour,

    Le code suivant fonctionne chez moi (remarque bien le cvCvtColor, h+1, w+1 et CV_64FC1 pour sqsum)

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    int main()
    {
        // Déclaration d'un pointeur sur IplImage :
        IplImage *image = cvLoadImage("Images/test6.bmp");
        IplImage *image_nvg = cvCreateImage(cvGetSize(image),8, 1);
        cvCvtColor(image,image_nvg,CV_BGR2GRAY);
     
        // Création d'une fenêtre dont la taille s'adapte à ce qu'elle contient :
        cvNamedWindow("Fenêtre", CV_WINDOW_AUTOSIZE);
     
        // Caractéristiques de l'image :
        int h = image->height;
        int w = image->width;
     
        // Déclaration de deux CvMat pour les calculs :
        CvMat* sum = cvCreateMat(h+1, w+1, CV_32FC1);
        //CvMat* sqsum = cvCreateMat(h, w, CV_32FC1);
        CvMat* sqsum = cvCreateMat(h+1, w+1, CV_64FC1);
     
        // Calcul de sum et sqsum à partir de l'image :
        cvIntegral(image_nvg, sum, sqsum);
     
    // [...]
    Ca marche aussi avec une image couleur. Les 3 canaux seront traités séparément. Il faut mettre CV_XXC3 mais ton cvmGet dans la suite du prog ne fonctionnera pas.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    int main()
    {
        // Déclaration d'un pointeur sur IplImage :
        IplImage *image = cvLoadImage("Images/test6.bmp");
        //IplImage *image_nvg = cvCreateImage(cvGetSize(image),8, 1);
        //cvCvtColor(image,image_nvg,CV_BGR2GRAY);
     
        // Création d'une fenêtre dont la taille s'adapte à ce qu'elle contient :
        cvNamedWindow("Fenêtre", CV_WINDOW_AUTOSIZE);
     
        // Caractéristiques de l'image :
        int h = image->height;
        int w = image->width;
     
        // Déclaration de deux CvMat pour les calculs :
        CvMat* sum = cvCreateMat(h+1, w+1, CV_32FC3);
        //CvMat* sqsum = cvCreateMat(h, w, CV_32FC1);
        CvMat* sqsum = cvCreateMat(h+1, w+1, CV_64FC3);
     
        // Calcul de sum et sqsum à partir de l'image :
        cvIntegral(image, sum, sqsum);
     
    // [...]
    Voila.

    Cordialement

Discussions similaires

  1. Problème à l'exécution avec Dev-C++
    Par HomerJr dans le forum OpenCV
    Réponses: 1
    Dernier message: 06/11/2007, 22h59
  2. [JCreator] Problème d'exécution avec jcreator
    Par dellal dans le forum Environnement de Développement Intégré (EDI)
    Réponses: 1
    Dernier message: 07/03/2007, 22h16
  3. Problème d'exécution avec Visual C++ Express
    Par LaseLiep dans le forum MFC
    Réponses: 4
    Dernier message: 03/04/2006, 10h16
  4. Problème d'exécution avec Dec C++
    Par PNL dans le forum C
    Réponses: 20
    Dernier message: 02/10/2005, 03h59
  5. Problème à l'exécution avec wxWindows (compilé avec BCC55)
    Par ShootDX dans le forum Autres éditeurs
    Réponses: 5
    Dernier message: 14/11/2003, 18h04

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo