Can't understand a class....

This is a discussion on Can't understand a class.... within the C++ Programming forums, part of the General Programming Boards category; I everybody! As the title says I'm having some problem trying to understand some pieces of code inside this class. ...

  1. #1
    Registered User
    Join Date
    Nov 2007
    Posts
    11

    Question Can't understand a class....

    I everybody!
    As the title says I'm having some problem trying to understand some pieces of code inside this class.
    I found this code in a book, which explains how the class works, but doesn't tell anything about syntax (in fact, it's not a C++ guide).

    Here's the code:

    Code:
    -------- .h file ---------
    
    template <typename TAG>
    class Handle
    {
    
    	union
    	{
    		enum
    		{
    			//Size to use for bit fields
    			MAX_BITS_INDEX = 16;
    			MAX_BITS_MAGIC = 16;
    			
    			//Size to compare against for asserting dereferences
    			MAX_INDEX = ( 1 << MAX_BITS_INDEX ) - 1 ;
    			MAX_MAGIC = ( 1 << MAX_BITS_MAGIC ) - 1 ;
    		};
    		
    		struct
    		{
    			unsigned m_Index : MAX_BITS_INDEX; //Index into resource array
    			unsigned m_Magic : MAX_BITS_MAGIC; //Magic number to check
    		};
    		
    		unsigned int m_Handle;
    	};
    	
    	
    	public:
    		Handle(void) : m_Handle(0);
    		void Init(unsigned int index);
    		
    		TUint GetIndex (void) const { return( m_Index ); }
    		TUint GetMagic (void) const { return( m_Magic ); }
    		TUint GetHandle (void) const { return( m_Handle ); }
    		bool isNull (void) const { return( !m_Handle ); }
    		
    		operator unsigned int ( void ) vonst { return (m_Handle) }
    };
    
    
    -------- .cpp file ---------
    
    template <typename TAG>
    void Handle <TAG> :: Init( unsigned int index )
    {
    	assert( IsNull() );
    	assert( index <= MAX_INDEX );
    	
    	static TUint s_AutoMagic = 0;
    	if( ++s_AutoMagic > MAX_MAGIC )
    		{
    			s_AutoMagic = 1;
    		}
    	
    	m_Index = index;
    	m_Magic = s_AutoMagic;
    }
    
    template <typename TAG>
    inline bool operator != ( vyg_Handle <TAG> l, vyg_Handle<TAG> r )
    {
    	return ( l.GetHandle() != r.GetHandle() );
    }
    
    template <typename TAG>
    inline bool operator == ( vyg_Handle <TAG> l, vyg_Handle<TAG> r )
    {
    	return ( l.GetHandle() == r.GetHandle() );
    }
    I'm not sure if about the usage of the union, enum and struct here.
    Starting from the union: it's anonymous (I know that) so this means that I can access its fields directly from a Handle object (ex: e.m_Handle).
    Then, since it's a union, all its members will be stored starting from the same location, allocating a space as large as the largest member inside the union.
    But here comes my question:
    - how does the enum and struct are interpreted at compile time?

    Furthermore when I compile it gives the following errors:

    `m_Handle' undeclared (first use this function) vygHandle.h line 40
    `m_Index' undeclared (first use this function) vygHandle.h line 38
    `m_Magic' undeclared (first use this function) vygHandle.h line 39
    ANSI C++ forbids in-class initialization of non-const static member `MAX_BITS_MAGIC' vygHandle.h line 17
    ANSI C++ forbids in-class initialization of non-const static member `MAX_INDEX' vygHandle.h line 20
    ANSI C++ forbids in-class initialization of non-const static member `MAX_MAGIC' vygHandle.h line 21
    confused by earlier errors, bailing out vygHandle.h line 41
    non-member function `GetHandle()' cannot have `const' method qualifier vygHandle.h line 40
    non-member function `GetIndex()' cannot have `const' method qualifier vygHandle.h line 38
    non-member function `GetMagic()' cannot have `const' method qualifier vygHandle.h line 39
    non-member function `isNull()' cannot have `const' method qualifier vygHandle.h line 41
    parse error before `;' vygHandle.h line 16
    parse error before `public' vygHandle.h line 34

    Could someone please help me here??
    Thx a lot!!
    Tesctassa
    Last edited by Tesctassa; 11-08-2007 at 11:02 AM. Reason: Some error in the original code I was asking about

  2. #2
    The larch
    Join Date
    May 2006
    Posts
    3,573
    One thing is that you cannot put template method implementations into a separate cpp file. They need to be defined in the header.

    Enums, as far as I can see, shouldn't take any memory per instance: these are constants that are shared between all instances.

    I guess that you are trying to create some sort of unique ID value, combining a counter and user-defined value. If so, why do you need all these complications? Just use a single int member (handle) and initialize it to the desired value in the Init method (or better in the constructor) without any unions or bitfields.
    I might be wrong.

    Thank you, anon. You sure know how to recognize different types of trees from quite a long way away.
    Quoted more than 1000 times (I hope).

  3. #3
    The larch
    Join Date
    May 2006
    Posts
    3,573
    After taking a closer look at the code, here's a version with the syntax errors fixed:

    Code:
    #include <iostream>
    #include <cassert>
    
    //C++ has no such thing as TUint
    typedef  unsigned TUint;
    
    template <typename TAG>
    class Handle
    {
        /*(unnamed) enum cannot be inside a union,
        enumerated items are separated by commas */
        enum
        {
            //Size to use for bit fields
            MAX_BITS_INDEX = 16,
            MAX_BITS_MAGIC = 16,
    		
            //Size to compare against for asserting dereferences
            MAX_INDEX = ( 1 << MAX_BITS_INDEX ) - 1 ,
            MAX_MAGIC = ( 1 << MAX_BITS_MAGIC ) - 1 
        };
    	union
    	{		
    		//you actually need an instance of this struct
                    struct
    		{
    			unsigned m_Index : MAX_BITS_INDEX; //Index into resource array
    			unsigned m_Magic : MAX_BITS_MAGIC; //Magic number to check
    		} m_struct;
    		
    		unsigned int m_Handle;
    	};
    	
    	
    	public:
    		Handle(void) : m_Handle(0) {}
    		void Init(unsigned int index);
    		
    		TUint GetIndex (void) const { return( m_struct.m_Index ); }
    		TUint GetMagic (void) const { return( m_struct.m_Magic ); }
    		TUint GetHandle (void) const { return( m_Handle ); }
    		bool IsNull (void) const { return( !m_Handle ); }
    		
    		operator unsigned int ( void ) const { return (m_Handle); }
    };
    
    //here you started to use vyg_Handle instead of Handle?
    template <typename TAG>
    void Handle <TAG> :: Init( TUint index )
    {
    	assert( IsNull() );
    	assert( index <= MAX_INDEX );
    	
    	static TUint s_AutoMagic = 0;
    	if( ++s_AutoMagic > MAX_MAGIC )
    		{
    			s_AutoMagic = 1;
    		}
    	
    	m_struct.m_Index = index;
    	m_struct.m_Magic = s_AutoMagic;
    }
    
    template <typename TAG>
    inline bool operator != ( Handle <TAG> l, Handle<TAG> r )
    {
    	return ( l.GetHandle() != r.GetHandle() );
    }
    
    template <typename TAG>
    inline bool operator == ( Handle <TAG> l, Handle<TAG> r )
    {
    	return ( l.GetHandle() == r.GetHandle() );
    }
    
    int main()
    {
        Handle<int> a, b;
        a.Init(24);
        b.Init(24);
        std::cout << a.GetIndex() << ' ' << a.GetMagic() << ' ' << a.GetHandle() << '\n';
        std::cout << b.GetIndex() << ' ' << b.GetMagic() << ' ' << b.GetHandle() << '\n';
    }
    Last edited by anon; 11-08-2007 at 10:47 AM.
    I might be wrong.

    Thank you, anon. You sure know how to recognize different types of trees from quite a long way away.
    Quoted more than 1000 times (I hope).

  4. #4
    Registered User
    Join Date
    Nov 2007
    Posts
    11
    Hi anon,

    first, thx for your answer! Second, two of the errors you pointed out, vyg_Handle and TUint weren't a bother (they were some data types I was using).
    About commas inside enum you were right... I mistaped those :P
    Regarding (unnamed) enum inside a union, I didn't know that.

    Thx again!
    Tesctassa

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Help with FIFO QUEUE
    By jackfraust in forum C++ Programming
    Replies: 23
    Last Post: 04-03-2009, 08:17 AM
  2. Class design problem
    By h3ro in forum C++ Programming
    Replies: 10
    Last Post: 12-19-2008, 08:10 AM
  3. Defining derivated class problem
    By mikahell in forum C++ Programming
    Replies: 9
    Last Post: 08-22-2007, 02:46 PM
  4. matrix class
    By shuo in forum C++ Programming
    Replies: 2
    Last Post: 07-13-2007, 01:03 AM
  5. Abstract class problem
    By VanJay011379 in forum C++ Programming
    Replies: 9
    Last Post: 07-31-2002, 01:30 PM

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21