hi there. i am on a UNIX system and am writing a template code called Array.h. it is called by a Test2.C file which does nothing more than declare a T object of type int. Array<int>.

i am getting all kinds of compile errors. have been over it and over it for about 8 hours now. can anyone help me here. i know there is something wrong with my non-member functions and i know there is something wrong with my init method that constructs my T's.

this is what i am getting from the compiler when i run Test2.C

Array.h:71: syntax error before `&' token
Array.h:71: `ostream' was not declared in this scope
Array.h:71: `os' was not declared in this scope
Array.h:71: syntax error before `<' token
Array.h:71: ISO C++ forbids declaration of `operator<<' with no type
Array.h:71: `int& operator<<(...)' must have an argument of class or enumerated
type
Array.h:71: `int& operator<<(...)' must take exactly two arguments
Array.h: In member function `void Array<T>::init(const T*, int)':
Array.h:349: syntax error before `;' token
Array.h: At global scope:
Array.h:366: syntax error before `>' token
Array.h:370: `b' was not declared in this scope
Array.h:370: syntax error before `;' token
Array.h:370: syntax error before `++' token

if anyone wanted to help me figure out what is going on with this mess that would be great. this is only PART A of what i need to be doing (ha ha).

and this is my Array.h of template T

#include <assert.h>
#include <iostream>                           // system files
                                              
#include "/unc/hedlund/121/lib/cpluslib.h"    // comp 121 library

                                              // GLOBAL CONSTANTS
const int NOT_FOUND = -1;                     // returned when para not in array
                                              
template<class T>
class Array
{                                                  
                                              
protected:
        static const int DEF_SIZE = 100;      // default array size
  
                                              
public:                                       // CONSTRUCTORS
                                              // default constructor
                                              // size = # of array elements
                                              // all elements initialized to 0
        Array ( int sz = DEF_SIZE );
                                              
                                              // copy constructor
                                              // new array is a deep copy of x
        Array ( const Array<T>& x );
                                              
        virtual ~Array();                     // destructor
        

                                              // OBSERVER FUNCTIONS
        int size() const;                     // return # of array elements  
        
                                              // equality-identical in size and
                                              // contents of each array element?
        bool operator == ( const Array<T> &rhs ) const;

                                              // inequality
        bool operator != ( const Array<T> &rhs ) const;
                                              
        bool invariant () const;              // is the object in a consistent state?
  
                                              // MUTABLE FUNCTIONS
                                              // assignment-contents of RHS are copied
                                              // to LHS (self)
        Array<T>& operator = ( const Array<T> &rhs );
  
                                              // index into array.  No bounds checking.
        T& operator [] ( int i ) const;
        
 
protected:
                                              // INTERNAL DATA REPRESENTATION
        int d_num_elements;                   // # of data elements

        T* d_array;  // ptr to first element of array
      
   
private:
                                              // PRIVATE MEMBER FUNCTIONS
                                                   [ Wrote 396 lines ]

classroom(52)% more Array.h

#include <assert.h>
#include <iostream>                           // system files
        
#include "/unc/hedlund/121/lib/cpluslib.h"    // comp 121 library

                                              // GLOBAL CONSTANTS
const int NOT_FOUND = -1;                     // returned when para not in array

template<class T>
class Array
{

protected:
        static const int DEF_SIZE = 100;      // default array size


public:                                       // CONSTRUCTORS
                                              // default constructor
                                              // size = # of array elements
                                              // all elements initialized to 0
        Array ( int sz = DEF_SIZE );

                                              // copy constructor
                                              // new array is a deep copy of x
        Array ( const Array<T>& x );
                                              
        virtual ~Array();                     // destructor


                                              // OBSERVER FUNCTIONS
        int size() const;                     // return # of array elements

                                              // equality-identical in size and
                                              // contents of each array element?
        bool operator == ( const Array<T> &rhs ) const;                  

                                              // inequality
        bool operator != ( const Array<T> &rhs ) const; 
                                               
        bool invariant () const;              // is the object in a consistent state?

                                              // MUTABLE FUNCTIONS
                                              // assignment-contents of RHS are copied
                                              // to LHS (self)
        Array<T>& operator = ( const Array<T> &rhs );

                                              // index into array.  No bounds checking.
        T& operator [] ( int i ) const;


protected:
                                              // INTERNAL DATA REPRESENTATION
        int d_num_elements;                   // # of data elements
        
        T* d_array;  // ptr to first element of array
       

private:
                                              // PRIVATE MEMBER FUNCTIONS
                                              // array initialization
        void init ( const T *x, int sz );
};


// 
// -------------------------NON-MEMBER FUNCTION PROTOTYPES-----------------------
//

        template<class T>                       // << displays array elements one per line
        ostream& operator << ( ostream& os, const Array<T> & b );

                                             // return first position of v in
        template<class T>                    // array b or NOT_FOUND if v not in array
        int includes ( const Array<T> &b, int v);


//
//
// ---------------------------------CONSTRUCTORS---------------------------------
//

//
// default constructor - initialize all elements to 0
// Parameters
//    INBOUND - sz = # of elements in array
// Pre - sufficient free memeory available AND ( 0 <= sz <= MAXINT)
// Post - creates a new array of sz elements AND sz == size() 
// Runtime - 0(n)
//
template<class T> 
Array<T>::
Array ( int sz )
{
                                                   // pre-condition assertion
        assert ( 0 <= sz <= MAXINT );              
        cout << "!!! IntArray default constructor called" <<endl;

                                                   // init() called to initialize d_array
                                                   // to 0 and d_num_elements to
                                                   // to DEF_SIZE or sz
        init ( T(), sz );
}


//
// copy constructor - make a deep copy of x
// Parameters
//    INBOUND - x = array to copy
// Pre - sufficient free memeory available
// Post - creates a new array of x.size() elements AND
//      AND self == x  AND old_self is deleted
// Runtime - 0(n)
// 
template<class T>
Array<T>::
Array ( const Array<T>& x )
{
        cout << "!!! IntArray copy constructor called" <<endl;
                                                   
                                                   // init() called to initialize d_array
                                                   // to x.d_array and d_num_elements
                                                   // to x.size()
        init ( x.d_array, x.size() );
}


//
// destructor - releases memory used
// Pre - TRUE
// Post - reclaim memory used for
// Runtime - 0(1)
// 
template<class T>
Array<T>::
~Array()
{                                               
                                                   // delete entire array d_array
        cout << "!!! IntArray destructor called" <<endl;
        if ( size() > 0 ) {
                delete [] d_array;
        }
}


//
//------------------------------OBSERVER FUNCTIONS-----------------------------
//


//
// size - returns the # of elements in an array
// Parameters
//    OUTBOUND - d_num_elements = number of elements in array
// Pre - TRUE
// Post - d_num_elements == size()
// Runtime - 0(1)
//
template<class T>
int Array<T>::
size () const
{
                                              // size of d_array is d_num_elements
        return (d_num_elements);

}  


//
// equality - are the 2 arrays identical?  They must match in size and
//          contents of each array element
// Parameters
//    INBOUND - rhs = RHS of equality
//    OUTBOUND - boolean true or false
// Pre - TRUE
// Post - if lhs == rhs return TRUE, else return FALSE
// Runtime - 0(n) worst case
// 
template<class T>
bool Array<T>::
operator == ( const Array<T> &rhs ) const
{
        if ( size() != rhs.size() ) {              // check for same # elements in      
                return ( FALSE );                  // lhs array and rhs array
        }
                                                   // if number of elements are equal
                                                   // check for the element contents of 
                                                   // lhs and rhs for equality
        int i = 0;     
cout<< "checking for equality" <<endl;                            
        while ( i < size() ){
                        // For all j: 0 .. i-1, self[j] == b[j]
                if ( self[i] != rhs[i] ){         
                        return ( FALSE );
                }
                else i++;
        }
        return ( TRUE );
}


//
// inequality - are the 2 arrays different?  They can differ in size
//     or contents of any array element
// Parameters
//    INBOUND - rhs = RHS of inequality
//    OUTBOUND - boolean true or false
// Pre - TRUE
// Post - if lhs != ths then return TRUE, else return FALSE
// Runtime - 0(n) worst case
//
template<class T>
bool Array<T>::
operator != ( const Array<T> &rhs) const
{
        if ( size() == rhs.size() ) {               // check for same # elements 
                return ( FALSE );                   // in lhs array and rhs array
        }
                                                    // if number of elements are not
                                                    // equal check the elements of 
                                                    // lhs and rhs for inequality

        int i = 0;
cout<< "checking for inequality" <<endl;
        while ( i < size() ){
                        // For all j: 0 .. i-1, self[j] != b[j]
                if ( self[i] == rhs[i] ){
                        return ( TRUE );
                } 
                else i++;
        }               
        return ( FALSE );
}


//
// invariant - is the object in a consistent state?
// Parameters - OUTBOUND - bool TRUE or FALSE
// Pre - TRUE
// Post - return TRUE if object is consistent, else return FALSE
// Runtime - 0(1)
//
template<class T>
bool Array<T>::  
invariant() const
{
        bool inv1 = (TRUE);                         // d_array doesn't point to NULL
        if ( d_array == NULL){                      // i.e. d_array has been initialized
                inv1 = (FALSE);
        }

        bool inv2 = (TRUE);                         // d_array is equal to itself
        if ( d_array != d_array ){
                inv2 = (FALSE);
        }

        bool inv3 = (TRUE);                         // d_num_elements is equal to 
        if ( d_num_elements != size() ){            // size()
                inv3 = (FALSE);
        }
                                                    // return true if all conditions 
                                                    // are true, else return false
        return ( inv1 && inv2 && inv3);      
}                                                  


//
//------------------------------MUTABLE FUNCTIONS----------------------------
//


// 
// assignment - make a deep copy of rhs into lhs
// Parameters 
//    INBOUND - rhs = RHS of assignment
//    OUTBOUND - new LHS object (deep copy of RHS)
// Pre - TRUE
// Post - self == rhs AND old_self is deleted
// Runtime - 0(n)
//
template<class T>
Array<T> & Array<T>::
operator = ( const Array<T> &rhs )
{
        if ( this == &rhs ){                      // check for assignment to itself
                return ( self );
        }
                                                  // free existing memory of lhs
        if (size() > 0 ){
                delete [] d_array;
        }
        init ( rhs.d_array, rhs.size() );         // initialize copy of rhs
        assert ( invariant() );                   // check that new object is valid
        return ( self );
}


//
// indexing - index into array.  No bounds checking
// Parameters -
//     INBOUND - int i = index #
//     OUTBOUND - object of type T 
// Pre - TRUE   (since no bounds checking)
// Post - object of type T in index i returned
// Runtime - 0(n)
//
template<class T>
T & Array<T>::                                                       
operator [] ( int i ) const                                                        
{
        if ( d_array == NULL ){
                return( NOT_FOUND );
        }
        else{                                                                            
                return d_array[i];
        }
}                           
  

//
//--------------------------PRIVATE MEMBER FUNCTIONS----------------------------
//                                    


// init - create and initialize a new array.  If an array is passed as the first 
// parameter          


                                              
template<class T>
void Array<T>::
init ( const T *data, int sz )
{

        assert ( (0 <= sz) && (sz <= MAXINT));

        d_num_elements = sz;
        if ( 0 == d_num_elements ){
                d_array = NULL;
        }
        else{
                d_array = new T [d_num_elements];

                assert ( NULL != d_array );
        }

        for (int i = 0; i < sz; i++ ){
                if ( NULL == data[i] ){
                        self [i] = T;
                }
                else{
                        self[i] = data[i];
                }
        }
        assert ( invariant() );
}

                      
//
//-----------------------------NON- MEMBER FUNCTIONS----------------------------
//


// << - display array elements one per line

template<classT>
ostream &
operator << ( ostream & os, const Array<T> & b )
{
        for ( int i = 0; i < b.size(); i++ ){

                os << b[i] << endl;
        }
        return ( os );
} 


// includes - returns position of first v in b

template<class T>
int 
includes ( const Array<T>& b, int v)
{
        int i = 0;

        while ( i <b.size() ){
                if ( b[i] == v ){
                        return i;
                }
                else{
                        i++
                }
        }
        return (NOT_FOUND);
}

and this is my Test2.C

int
main()
{

      


        cout<< "*******Declaration of 3 IntArray objects/size() checking******* \n" <<endl;

        cout<< "IntArray a declared with no parameters" <<endl;

        Array<int> a;
        cout << "   " <<endl;

return 0;
}

thanks
crq

First, place this after your includes:

using namespace std;

Then look for typos. Recompile and we'll go from there.

p.s. It couldn't hurt to read my reply to your other thread. Notice how I used T(), not T, for default construction of a value of template parameter type.

thanks for looking at this ...

this is Test2.C

#include <assert.h>
#include <iostream>
#include "Array.h"

#include "/unc/hedlund/121/lib/cpluslib.h"

using namespace std;

int
main()
{




        cout<< "*******Declaration of 3 IntArray objects/size() checking******* \n" <<endl;

        cout<< "IntArray a declared with no parameters" <<endl;

        Array<int> a;
        cout << "   " <<endl;

return 0;
}

and the Array.h is the same except for putting the

using namespace std;

after the includes and putting the () after the T in the init method.

and this is what the compiler says ...

hmmm... syntax error. that is usually a goof error. are the numbers at the side line numbers? anyone know how to turn on the line numbers in pico?

In file included from Test2.C:4:
Array.h:367: syntax error before `>' token
Array.h:371: `b' was not declared in this scope
Array.h:371: syntax error before `;' token
Array.h:371: syntax error before `++' token
Array.h:384: too many template parameter lists in declaration of `int
includes(const Array<T>&, int)'
Array.h:384: syntax error before `{' token
Test2.C:12: cannot declare `::main' to be a template
Test2.C:12: confused by earlier errors, bailing out

thanks for looking at this!! ... i appreciate it more than you can ever know. really.

crq

Look, everytime you use a standard C++ name (like ostream), it needs to be qualified by std::, or have a using declaration or using directive before you use it. I was trying to give you the most expedient solution, but you didn't do it right. Generally, std:: is used for headers, and for source files you can do what you want:

// class.h
#include <iostream>

class C {
  // Stuff
  friend std::ostream& operator<<(ostream& out, const C& c);
  friend std::istream& operator>>(istream& in, C& c);
};
// class.cpp
#include "class.h"

using std::ostream;
using std::istream;

ostream& operator<<(ostream& out, const C& c)
{
  // Implementation
}

istream& operator>>(istream& in, C& c)
{
  // Implementation
}
// main.cpp
#include <iostream>
#include "class.h"

using namespace std;

int main()
{
  // Stuff
}

Your primary problem is that you failed to do this properly, so the compiler doesn't recognize unqualified names from the std namespace. Once you fix this, the real errors will be easier to find.

// class.h
#include <iostream>

class C {
  // Stuff
  friend std::ostream& operator<<(ostream& out, const C& c);
  friend std::istream& operator>>(istream& in, C& c);
};

i tried this in my Array.h template class file. but i am supposed to use ostream overloading in a non-member function. so the friend wasn't accepted by my compiler. that's why i am having trouble figuring this out. template/non-member functions/and ostream overloading is a bit out of my league at this point.

thanks
crq

Edited 3 Years Ago by Dani: Formatting fixed

// class.h
#include <iostream>

class C {
  // Stuff
  friend std::ostream& operator<<(ostream& out, const C& c);
  friend std::istream& operator>>(istream& in, C& c);
};

i tried this in my Array.h template class file. but i am supposed to use ostream overloading in a non-member function. so the friend wasn't accepted by my compiler. that's why i am having trouble figuring this out. template/non-member functions/and ostream overloading is a bit out of my league at this point.

thanks
crq

sorry, i don't know how i put that little wierd face in the code ...

crq

Edited 3 Years Ago by pyTony: format

>but i am supposed to use ostream overloading in a non-member function.
Friend functions are not member functions. They are non-member functions that have access to the private members of the class.

>so the friend wasn't accepted by my compiler
Well, I have no idea what's wrong with your code because you use a stupid non-standard header file that declares equally stupid things. Since I don't have the header, I can't compile your code.

>but i am supposed to use ostream overloading in a non-member function.
Friend functions are not member functions. They are non-member functions that have access to the private members of the class.

>so the friend wasn't accepted by my compiler
Well, I have no idea what's wrong with your code because you use a stupid non-standard header file that declares equally stupid things. Since I don't have the header, I can't compile your code.

i am using the skeleton that my instructor provided. i am not very excited about the way he has laid this stuff out either. i am just trying to stay within the rules that he has set for me. but i won't bother asking anymore questions on here. you seem to enjoy the saying nasty things to me ... but i guess you only do that to us "stupid" people.

thanks
crq

>i am just trying to stay within the rules that he has set for me.
Posting code that uses declarations in a header that you don't provide isn't very helpful. At the very least, you could post /unc/hedlund/121/lib/cpluslib.h so that I know what parts are due to a retarded instructor and what parts are actual errors.

>you seem to enjoy the saying nasty things to me
If I recall correctly, the only thing nasty I said was in reference to your instructor's header file. But if you don't want my help, as seems to be the case with people who quickly take offense at nothing, I won't offer it. Your loss.

This article has been dead for over six months. Start a new discussion instead.