Problem accessing variable in inherited template class

Collapse
X
 
  • Time
  • Show
Clear All
new posts
  • djsuson
    New Member
    • Jun 2008
    • 2

    Problem accessing variable in inherited template class

    I'm trying to set up an inheritance tree that also uses templates. This is an attempt to simplify some previous code that was filled with redundancies. I'm working with g++ 3.4.6. The code is split over four files: two headers and two implamentation files, but uses the include trick mentioned on another thread to connect the header and implamentation files together. The base class header is

    Code:
    #ifndef _BASEDATA_H_
    #define _BASEDATA_H_
    
    #include <vector>
    #include <string>
    #include <fstream>
    
    template <typename _Type> class baseData
    {
    public:
      baseData();
      virtual ~baseData() {}
    
    public:
    
      /**
       * get human readable status
       */
       std::string status();
    
      /**
       * access data vector
       */
      std::vector<_Type>* access() {return &m_data;}
    
      /**
       * reset data vector
       */
       void reset();
    
      /**
       * overload [] operator
       */
       _Type& operator[](long i) {return m_data[i];}
    
    protected:
      std::vector<_Type> m_data;
      unsigned int       m_status;
    };
    
    #ifndef USE_EXPORT_KEYWORD
    #include "basedata.cpp"
    #endif
    
    #endif
    while the corresponding cpp file is

    Code:
    #ifndef USE_EXPORT_KEYWORD
    #define export
    #endif
    
    export
    template <typename _Type> baseData<_Type>::baseData()
    {
      m_status = 0;
    }
    
    export
    template <typename _Type> std::string baseData<_Type>::status()
    {
      std::string reason;
      switch (m_status)
      {
        case 1:
          reason = "Could not open input file";
          break;
        case 2:
          reason = "Could not open output file";
          break;
        case 3:
          reason = "Requested data size larger than maximum allocatable size";
          break;
        case 4:
          reason = "No raw data to synchronize to";
          break;
        default:
          reason = "OK";
          break;
      };
      return reason;
    }
    
    export
    template <typename _Type> void baseData<_Type>::reset()
    {
      m_data.resize(0);
    }
    
    #ifndef USE_EXPORT_KEYWORD
    #undef export
    #endif
    Similarly, the inheriting class' header is

    Code:
    #ifndef _MATRIXDATA_H_
    #define _MATRIXDATA_H_
    
    #include <vector>
    #include <string>
    
    #include "basedata.h"
    
    template <typename _Type> class matrixData : public baseData< std::vector<_Type> >
    {
    
    public:
      matrixData();
      ~matrixData() {}
    
    public:
      /**
       * Initialize data set to zeros
       */
       int initialize(int nRows, int nCols, int row_0 = 0, int col_0 = 0);
    
      /**
       * access data size
       */
       long rows() {return baseData<_Type>::access()->size();}
       long rows(long newRows);
    
       long cols() {return (*(baseData<_Type>::access()))[0].size();}
       long cols(long newCols);
    
       long size() {return rows()*cols();}
       long size(long newSize);
    
    private:
    
      int       m_colMax;
      int       m_colMin;
      int       m_rowMax;
      int       m_rowMin;
    };
    
    #ifndef USE_EXPORT_KEYWORD
    #include "matrixdata.cpp"
    #endif
    
    #endif
    while the associated cpp file is

    Code:
    #include <fstream>
    #include <stdio.h>
    #include <math.h>
    
    #ifndef USE_EXPORT_KEYWORD
    #define export
    #endif
    
    export
    template <typename _Type> matrixData<_Type>::matrixData()
    {
      m_colMax = m_colMin = 0;
      m_rowMax = m_rowMin = 0;
    }
    
    export
    template <typename _Type> int matrixData<_Type>::initialize(int nRows, int nCols, int row_0, int col_0)
    {
      int i, j;
      int dataSize;
      unsigned int highMask = 0xFFFF0000;
      unsigned int lowMask = 0x0000FFFF;
    
      m_rowMax = nRows;
      m_colMax = nCols;
      m_rowMin = row_0;
      m_colMin = col_0;
    
      /*
         Note that in matrix[i][j], i denotes the number of rows in the column, while j denotes the number of columns
         in the matrix. Therefore, want to deal with the datasize so that the high part is the number of rows, while
         the low part is the number of columns.
      */
    
      dataSize = (((m_rowMax - m_rowMin) << 16) & highMask) + ((m_colMax - m_colMin) & lowMask);
      if (size(dataSize) < 0)
      {
        m_status = 3;
        return -1;
      }
    
      _Type value = (_Type) NULL;
      for (i = m_rowMin;i < m_rowMax;i++)
        for (j = m_colMin;j < m_colMax;j++)
        {
          if (m_data.begin()+i == m_data.end())
          {
            std::vector<_Type> newColumn;
            m_data.push_back(newColumn);
            if (m_data[i].begin()+j == m_data[i].end())
              m_data[i].push_back(value);
          }
          else
            m_data[i][j] = value;
        }
    
      return size();
    }
    
    export
    template <typename _Type> long matrixData<_Type>::size(long newSize)
    {
      unsigned long highMask = 0xFFFF0000;
      unsigned long lowMask = 0x0000FFFF;
      unsigned long rowSize, columnSize;
      unsigned long i;
    
      rowSize = (newSize & highMask) >> 16;
      columnSize = newSize & lowMask;
      if (rowSize > m_data.max_size())
      {
        m_status = 3;
        return -1;
      }
      m_data.resize(rowSize);
      for (i = 0;i < rowSize;i++)
      {
        if (columnSize > m_data[i].max_size())
        {
          m_status = 3;
          return -1;
        }
        m_data[i].resize(columnSize);
      }
    
      return size();
    }
    
    export
    template <typename _Type> long matrixData<_Type>::rows(long newRows)
    {
      if (newRows > m_data.max_size())
      {
        m_status = 3;
        return -1;
      }
      m_data.resize(newRows);
    
      return m_data.size();
    }
    
    export
    template <typename _Type> long matrixData<_Type>::cols(long newCols)
    {
      if (newCols > m_data[0].max_size())
      {
        m_status = 3;
        return -1;
      }
    
      int i;
      for (i = 0;i < m_data.size();i++)
        m_data[i].resize(newCols);
    
      return m_data[0].size();
    }
    
    #ifndef USE_EXPORT_KEYWORD
    #undef export
    #endif
    When I try to compile this, I get the following error message:

    error: 'm_status' was not declared in this scope

    Previously, I had a number of (nearly) identical classes that inherited from baseData, where the main difference was in what _Type was declared to be. In that case, I had no problem accessing m_status. While I'm fairly sure this indicates a template verses non-template difference, I don't see how to fix this so that I can reduce my redundant classes. Any help would be appreciated.

    Thanks,
    Dan
  • Banfa
    Recognized Expert Expert
    • Feb 2006
    • 9067

    #2
    On which line of code in which file do you get the error?

    Comment

    • djsuson
      New Member
      • Jun 2008
      • 2

      #3
      Line 38 of the matrixData class cpp code

      Comment

      • RRick
        Recognized Expert Contributor
        • Feb 2007
        • 463

        #4
        I don't know if this will fix your error, but first you must combine the header and source code for each object into a single header file. Most compilers (including GNU and windows) can not deal with them separately.

        If you simply append the two files together, remember to make each method inline.

        This might solve the problem.

        Comment

        Working...