sample error:
"Array2.h": Array2.h friend declaration `std:stream& at line 13
operator<<(std:stream&, const Array<T, numberOfElements>&)' declares a non-template function
What could the problem be?
Code:#ifdef __BORLANDC__ #pragma argsused #endif #include <iostream> using std::cout; using std::endl; #include "Array2.h" int main( int argc, char * argv[]) { Array<int, 6 > numbers; cout << numbers.getSize() << endl; for( int i = 0; i < 6; i++ ){ numbers[i] = i; } cout << numbers << endl; return 0; }Code:// Fig. 8.4: array1.h // Simple class Array (for integers) #ifndef ARRAY1_H #define ARRAY1_H #include <iostream> using std::ostream; using std::istream; template <class T, int numberOfElements = 10> class Array { friend ostream &operator<<( ostream &, const Array<T,numberOfElements> & ); friend istream &operator>>( istream &, Array<T,numberOfElements> & ); public: Array<T,numberOfElements>(); // default constructor Array( const Array<T,numberOfElements> & ); // copy constructor ~Array<T,numberOfElements>(); // destructor int getSize() const; // return size const Array<T,numberOfElements> &operator=( const Array<T,numberOfElements> & ); // assign arrays bool operator==( const Array<T,numberOfElements> & ) const; // compare equal // Determine if two arrays are not equal and // return true, otherwise return false (uses operator==). bool operator!=( const Array<T,numberOfElements> &right ) const { return ! ( *this == right ); } T &operator[]( int ); // subscript operator const T &operator[]( int ) const; // subscript operator static int getArrayCount(); // Return count of // arrays instantiated. private: int size; // size of the array T *ptr; // pointer to first element of array static int arrayCount; // # of Arrays instantiated }; // Fig 8.4: array1.cpp // Member function definitions for class Array #include <iostream> using std::cout; using std::cin; using std::endl; #include <iomanip> using std::setw; #include <cstdlib> #include <cassert> //#include "array1.h" // Initialize static data member at file scope template <class T, int numberOfElements> int Array< T,numberOfElements>::arrayCount = 0; // no objects yet // Default constructor for class Array (default size 10) template <class T, int numberOfElements > Array<T,numberOfElements>::Array() { size = ( numberOfElements > 0 ? numberOfElements : 10 ); ptr = new T[ size ]; // create space for array assert( ptr != 0 ); // terminate if memory not allocated ++arrayCount; // count one more object for ( int i = 0; i < size; i++ ) ptr[ i ] = 0; // initialize array } // Copy constructor for class Array // must receive a reference to prevent infinite recursion template <class T, int numberOfElements > Array<T,numberOfElements>::Array( const Array<T,numberOfElements> &init ) : size( init.size ) { ptr = new T[ size ]; // create space for array assert( ptr != 0 ); // terminate if memory not allocated ++arrayCount; // count one more object for ( int i = 0; i < size; i++ ) ptr[ i ] = init.ptr[ i ]; // copy init into object } // Destructor for class Array template <class T, int numberOfElements> Array<T,numberOfElements>::~Array() { delete [] ptr; // reclaim space for array --arrayCount; // one fewer objects } // Get the size of the array template <class T, int numberOfElements> int Array<T,numberOfElements>::getSize() const { return size; } // Overloaded assignment operator // const return avoids: ( a1 = a2 ) = a3 template <class T, int numberOfElements> const Array<T,numberOfElements> &Array<T,numberOfElements>::operator=( const Array<T,numberOfElements> &right ) { if ( &right != this ) { // check for self-assignment // for arrays of different sizes, deallocate original // left side array, then allocate new left side array. if ( size != right.size ) { delete [] ptr; // reclaim space size = right.size; // resize this object ptr = new T[ size ]; // create space for array copy assert( ptr != 0 ); // terminate if not allocated } for ( int i = 0; i < size; i++ ) ptr[ i ] = right.ptr[ i ]; // copy array into object } return *this; // enables x = y = z; } // Determine if two arrays are equal and // return true, otherwise return false. template <class T, int numberOfElements> bool Array<T,numberOfElements>::operator==( const Array<T,numberOfElements> &right ) const { if ( size != right.size ) return false; // arrays of different sizes for ( int i = 0; i < size; i++ ) if ( ptr[ i ] != right.ptr[ i ] ) return false; // arrays are not equal return true; // arrays are equal } // Overloaded subscript operator for non-const Arrays // reference return creates an lvalue template <class T, int numberOfElements> T &Array<T,numberOfElements>::operator[]( int subscript ) { // check for subscript out of range error assert( 0 <= subscript && subscript < size ); return ptr[ subscript ]; // reference return } // Overloaded subscript operator for const Arrays // const reference return creates an rvalue template <class T, int numberOfElements> const T &Array<T,numberOfElements>::operator[]( int subscript ) const { // check for subscript out of range error assert( 0 <= subscript && subscript < size ); return ptr[ subscript ]; // const reference return } // Return the number of Array objects instantiated // static functions cannot be const template <class T, int numberOfElements> int Array<T,numberOfElements>::getArrayCount() { return arrayCount; } // Overloaded input operator for class Array; // inputs values for entire array. template <class T, int numberOfElements> istream &operator>>( istream &input, Array<T,numberOfElements> &a ) { for ( int i = 0; i < a.size; i++ ) input >> a.ptr[ i ]; return input; // enables cin >> x >> y; } // Overloaded output operator for class Array template <class T, int numberOfElements> ostream &operator<<( ostream &output, const Array<T,numberOfElements> &a ) { int i; for ( i = 0; i < a.size; i++ ) { output << setw( 12 ) << a.ptr[ i ]; if ( ( i + 1 ) % 4 == 0 ) // 4 numbers per row of output output << endl; } if ( i % 4 != 0 ) output << endl; return output; // enables cout << x << y; } #endif



LinkBack URL
About LinkBacks
stream& at line 13


