2012-12-18 29 views
0

我,只有當我運行程序的IDE外面發生一個奇怪的接入位置錯誤(我用的代碼::塊王氏GNU GCC編譯器和GBD作爲調試器)。訪問衝突讀取位置僅在釋放模式「地址」當一個std插入元素::地圖

Unhandled exception at 0x77cd82ea in SFinGe.exe: 0xC0000005: Access violation reading location 0x69687065. 

發生這種情況時,我嘗試將元素添加到一個std ::地圖。我知道這種情況通常發生在你有單位變量的時候,但我一直在仔細檢查我的代碼,我無法找到問題,並且它讓我感到沮喪。

這是類定義:

//============================================================================== 
// CDirectionalMapGenerator prototypes. 
//============================================================================== 

#ifndef CDIRECTIONALMAPGENERATOR_H 
#define CDIRECTIONALMAPGENERATOR_H 

//============================================================================== 

#include <complex.h> 
#include <math.h> 
#include <map> 
#include <vector> 
#include <CRandom.h> 
#include <SFingerprintPattern.h> 
#include <ESingularityType.h> 

//============================================================================== 

#define PI 3.14159265359 

//============================================================================== 

/** \brief 
    * Generates a directional map using the orientation model proposed by Sherlock and Monro, this allows a consistent orientation image to be computed from 
    * the knowledge of the position of the fingerprint singularities (core and deltas) alone. The image is located in the complex plane and the local ridge 
    * orientation is the phase of the square root of a complex rational function whose singularities (poles and zeros) are located at the same place 
    * as the fingerprint singularities. 
*/ 
class CDirectionalMapGenerator 
{ 
    public: 

    /** \brief 
    * Initializes a new instance of the CDirectionalMapGenerator class. 
    * 
    */ 
    CDirectionalMapGenerator(); 

    /** \brief 
    * Destroy the CDirectionalMapGenerator object and all its reference safely. 
    */ 
    virtual ~CDirectionalMapGenerator(); 

    /** \brief 
    * Generates a directional map. 
    * \param pattern CFingerprintPattern The fingerprint class and singularity types information. 
    * \param witdh int The witdh of the map. 
    * \param height int The height of the map. 
    * \return std::vector<std::vector<double>> The directional map. 
    */ 
    std::vector<std::vector<double> > generate(SFingerprintPattern& pattern, int width, int height); 

    private: 

    /** \brief 
    * Gets the segment orientation. 
    * \param z complex The complex number representing a point in the directional map. 
    * \return double The segment orientation in radians. 
    */ 
    double getSegmentOrientation(std::complex<double> z); 

    /** \brief 
    * Vizcaya and Gerhardt correction. 
    * \param alpha double The angle to be corrected. 
    * \param singularityType ESingularityType The singularity type. 
    * \return double The angle corrected. 
    */ 
    double correctOrientation(double alpha, ESingularityType singularityType); 

    /** \brief 
    * Gets the amount of angle correction for the given point. The directional map is uniformly divided between -PI and PI 
    * in eight segments (45 degrees each segment), points in each region must be adjusted using a different piecewise linear function. 
    * The variables 'v' and 'u' are angles defined at the beginning of the generation process, this angles are chosen depending on the 
    * singularity type and fingerprint class. 
    * \param q int Region of the point. 
    * \param singularityType ESingularityType The singularity type. 
    * \return double The amount of correction. 
    */ 
    double getAmountOfCorrection(int q, ESingularityType singularityType); 

    /** \brief 
    * Modification angles must be defined on the basis of position and number of singularities. 
    * \return void 
    * 
    */ 
    void generateWeigths(); 

    private: 
     static CRandom*     m_sRandom; 

     std::map<ESingularityType, double> m_v; 
     std::map<ESingularityType, double> m_u; 
     EFingerprintClass     m_currentFingerprintClass; 
     SFingerprintPattern    m_currentPattern; 
     double        m_nArchTypeFactors[3]; 
     int        m_nCurrentWidth; 
     int        m_nCurrentHeight; 
}; 


#endif // CDIRECTIONALMAPGENERATOR_H 

和實現:

#include "CDirectionalMapGenerator.h" 
//============================================================================== 

// Static variable initialization. 
CRandom* CDirectionalMapGenerator::m_sRandom = new CRandom(time(0)); 

//============================================================================== 
CDirectionalMapGenerator::CDirectionalMapGenerator() 
{ 
    m_currentFingerprintClass = ARCH; 
    m_nCurrentWidth   = 0; 
    m_nCurrentHeight   = 0; 
    m_v      = std::map<ESingularityType, double>(); 
    m_u      = std::map<ESingularityType, double>(); 
} 

//============================================================================== 
CDirectionalMapGenerator::~CDirectionalMapGenerator() 
{ 
    delete m_sRandom; 

    m_u.clear(); 
    m_v.clear(); 
} 

//============================================================================== 
std::vector<std::vector<double> > CDirectionalMapGenerator::generate(SFingerprintPattern& pattern, int width, int height) 
{ 
    std::vector<std::vector<double> > directionalMap; 

    m_currentFingerprintClass = pattern.FingerprintClass; 
    m_currentPattern   = pattern; 
    m_nCurrentWidth   = width; 
    m_nCurrentHeight   = height; 

    // Clear weights from last generation. 
    m_u.clear(); 
    m_v.clear(); 

    this->generateWeigths(); 

    for (int i = 0; i < m_nCurrentWidth; ++i) 
    { 
     std::vector<double> vLine; 
     for (int j = 0; j < m_nCurrentHeight; ++j) 
     { 
     std::complex<double> z(i, j); 

     vLine.push_back(this->getSegmentOrientation(z)); 
     } 

     directionalMap.push_back(vLine); 
    } 

    return directionalMap; 
} 


//============================================================================== 
double CDirectionalMapGenerator::getSegmentOrientation(std::complex<double> z) 
{ 
     double segmentOrientation = 0; 
     int degrees   = 0; 

     if (m_currentFingerprintClass == ARCH) 
     { 
     // Arch patterns that do not contain any singularity are not supported by the model, a sinusoidal function 
     // must be use instead (The frequency and amplitude are tuned to control the arch curvature and aspect). 
     segmentOrientation = atan(std::max(0.0, (m_nArchTypeFactors[2] - m_nArchTypeFactors[2] * z.imag()/(m_nCurrentHeight * m_nArchTypeFactors[1]))) * cos(z.real() * PI/(m_nCurrentWidth * m_nArchTypeFactors[0]))); 
     } 
     else if (m_currentFingerprintClass == WHORL) 
     { 
     // Whorl have two cores and two deltas. 

     // 1/2(g(arg(z - d1)) - g(arg(z - l1))) + 1/2(g(arg(z - d2)) - g(arg (z - l2))) 
     segmentOrientation = (0.5 * (this->correctOrientation(arg((z - m_currentPattern.DeltaOne)), DELTA) - this->correctOrientation(arg((z - m_currentPattern.LoopOne)), CORE))) + 
          (0.5 * (this->correctOrientation(arg((z - m_currentPattern.DeltaTwo)), SECONDARY_DELTA) - this->correctOrientation(arg((z - m_currentPattern.LoopTwo)), SECONDARY_CORE))); 
     } 
     else 
     { 
     // 1/2(g(arg(z - d)) - g(arg (z - l))) 
     segmentOrientation = 0.5 * (this->correctOrientation(arg((z - m_currentPattern.DeltaOne)), DELTA) - this->correctOrientation(arg((z - m_currentPattern.LoopOne)), CORE)); 
     } 

     degrees = static_cast<int>(segmentOrientation * (180/PI)); // From radiants to degrees. 

     if(degrees < 0) 
     degrees = -(((-1) * degrees) % (180)) + 180; 

     segmentOrientation = degrees * (PI/180); // From degrees to radiants. 

     return segmentOrientation; 
} 

//============================================================================== 
double CDirectionalMapGenerator::correctOrientation(double alpha, ESingularityType singularityType) 
{ 
     int q    = static_cast<int>(floor(4 * (PI + alpha)/PI)); 
     double alphaI  = -PI + (PI * q)/4; 
     double correctionOne = this->getAmountOfCorrection(q + 1, singularityType); //gk(alpha i) 
     double correctionTwo = this->getAmountOfCorrection(q + 2, singularityType); //gk(alpha i + 1) 

     return (correctionOne + ((4 * (alpha - alphaI))/PI) * (correctionTwo - correctionOne)); 
} 

//============================================================================== 
double CDirectionalMapGenerator::getAmountOfCorrection(int q, ESingularityType singularityType) 
{ 
     double amountOfCorrection = 0; 
     switch (q) 
     { 
     case 1: 
      amountOfCorrection = -PI + m_u[singularityType]; 
      break; 
     case 2: 
      amountOfCorrection = -3 * PI/4 + m_u[singularityType]; 
      break; 
     case 3: 
      amountOfCorrection = -PI/2; 
      break; 
     case 4: 
      amountOfCorrection = -PI/4 + m_v[singularityType]; 
      break; 
     case 5: 
      amountOfCorrection = m_v[singularityType]; 
      break; 
     case 6: 
      amountOfCorrection = PI/4 + m_v[singularityType]; 
      break; 
     case 7: 
      amountOfCorrection = PI/2; 
      break; 
     case 8: 
      amountOfCorrection = 3 * PI/4 + m_u[singularityType]; 
      break; 
     default: 
      amountOfCorrection = PI + m_u[singularityType]; 
      break; 
     } 

     return amountOfCorrection; 
} 

//============================================================================== 
void CDirectionalMapGenerator::generateWeigths() 
{ 
     switch (m_currentFingerprintClass) 
     { 
     case(ARCH): 

      m_nArchTypeFactors[0] = (0.8 + 0.4 * m_sRandom->nextDouble()); 
      m_nArchTypeFactors[1] = (0.6 + 0.8 * m_sRandom->nextDouble()); 
      m_nArchTypeFactors[2] = (1.2 + m_sRandom->nextDouble() * 1.5); 

     break; 
     case (LEFT_LOOP): 

      m_u[CORE] = -120 * PI/180.0 + m_sRandom->nextDouble() * (45 * PI/180.0); 
      m_v[CORE] = 50 * PI/180.0 + m_sRandom->nextDouble() * (45 * PI/180.0); 

     break; 
     case (RIGHT_LOOP): 

      m_u[CORE] = -90 * PI/180.0 + m_sRandom->nextDouble() * (45 * PI/180.0); 
      m_v[CORE] = 60 * PI/180.0 + m_sRandom->nextDouble() * (45 * PI/180.0); 

     break; 
     case (TENTED_ARCH): 

      m_u[CORE] = -90 * PI/180.0 + m_sRandom->nextDouble() * (45 * PI/180.0); 
      m_v[CORE] = 45 * PI/180.0 + m_sRandom->nextDouble() * (45 * PI/180.0); 

     break; 
     case (WHORL): 

      // Whorl have two cores and two deltas. 
      m_u[CORE] = -60 * PI/180.0 + m_sRandom->nextDouble() * (15 * PI/180.0); 
      m_v[CORE] = 40 * PI/180.0 + m_sRandom->nextDouble() * (15 * PI/180.0); 
      m_u[SECONDARY_CORE] = 10 * PI/180.0 + m_sRandom->nextDouble() * (15 * PI/180.0); 
      m_v[SECONDARY_CORE] = 20 * PI/180.0 + m_sRandom->nextDouble() * (15 * PI/180.0); 

     break; 
     } 
      m_u[DELTA] = 0; 
      m_v[DELTA] = 0; 
      m_u[SECONDARY_DELTA] = 0; 
      m_v[SECONDARY_DELTA] = 0; 
} 

這是一個突破方法:

void CDirectionalMapGenerator::generateWeigths() 
{ 
     switch (m_currentFingerprintClass) 
     { 
     case(ARCH): 

      m_nArchTypeFactors[0] = (0.8 + 0.4 * m_sRandom->nextDouble()); 
      m_nArchTypeFactors[1] = (0.6 + 0.8 * m_sRandom->nextDouble()); 
      m_nArchTypeFactors[2] = (1.2 + m_sRandom->nextDouble() * 1.5); 

     break; 
     case (LEFT_LOOP): 

      m_u[CORE] = -120 * PI/180.0 + m_sRandom->nextDouble() * (45 * PI/180.0); 
      m_v[CORE] = 50 * PI/180.0 + m_sRandom->nextDouble() * (45 * PI/180.0); 

     break; 
     case (RIGHT_LOOP): 

      m_u[CORE] = -90 * PI/180.0 + m_sRandom->nextDouble() * (45 * PI/180.0); 
      m_v[CORE] = 60 * PI/180.0 + m_sRandom->nextDouble() * (45 * PI/180.0); 

     break; 
     case (TENTED_ARCH): 

      m_u[CORE] = -90 * PI/180.0 + m_sRandom->nextDouble() * (45 * PI/180.0); 
      m_v[CORE] = 45 * PI/180.0 + m_sRandom->nextDouble() * (45 * PI/180.0); 

     break; 
     case (WHORL): 

      // Whorl have two cores and two deltas. 
      m_u[CORE] = -60 * PI/180.0 + m_sRandom->nextDouble() * (15 * PI/180.0); 
      m_v[CORE] = 40 * PI/180.0 + m_sRandom->nextDouble() * (15 * PI/180.0); 
      m_u[SECONDARY_CORE] = 10 * PI/180.0 + m_sRandom->nextDouble() * (15 * PI/180.0); 
      m_v[SECONDARY_CORE] = 20 * PI/180.0 + m_sRandom->nextDouble() * (15 * PI/180.0); 

     break; 
     } 
      m_u[DELTA] = 0; 
      m_v[DELTA] = 0; 
      m_u[SECONDARY_DELTA] = 0; 
      m_v[SECONDARY_DELTA] = 0; 
} 

當過我嘗試指派價值到它吹的地圖:

m_u[CORE] = -90 * PI/180.0 + m_sRandom->nextDouble() * (45 * PI/180.0); 

林不知道什麼撥錯,我初始化需要它的構造器中的所有成員,所有的人都作爲參數傳遞給方法「產生」通過。

我能會丟失?

+0

的std ::地圖默認使用小於(<)運算符比較密鑰。也許ESingularityType :: operator <?有問題。 –

回答

3

你在程序中使用兩個CDirectionalMapGenerator S'您的靜態變量m_sRandom是在節目的開頭只new編一次,但delete d每當CDirectionalMapGenerator被破壞。如果創建後的第一個第二CDirectionalMapGenerator被破壞,無論何時訪問m_sRandom你會訪問一個空指針。

要麼確保你沒有deletem_sRandom指針,直到你的程序結束或使它非靜態,以使CDirectionalMapGenerator的每個實例都有自己的副本。

+0

哦,太好了抓我沒有意識到這一點,但只有一個CDirectionalMapGenerator的實例,它只是被破壞了程序結束時,我會請從解構壽刪除,謝謝! – AngelCastillo

+0

你確定它是那一行嗎?也許'nextDouble'是違法功能? –

+0

我與法內COUT測試的隨機數發生器及其工作正常,還當我嘗試assing喜歡「4」的地圖,它的衝擊值,因此即時通訊相當肯定的是一些相關的地圖,但不能圖。什麼=((順便說一句+1的靜態成員在尖端正在構造破壞:d) – AngelCastillo