How to make a pointer to class and how to use it?

Like, what would the cout statements show on screen?

#include <iostream.h>

void main()
{
    class CLASS
    {
        public:
        int INT;
        char CHAR;
    };

    CLASS OBJECT;
    OBJECT.INT = 10;
    OBJECT.CHAR = 'A';

    CLASS *POINTER = &OBJECT;
    cout << POINTER << " " << &OBJECT; //WILL THESE TWO SHOW 
                                       //THE SAME VALUE?

    cout << endl << *POINTER << " " << OBJECT.INT << " " << POINTER -> INT; //WILL THESE SHOW THE SAME?

    cout << endl << *(POINTER + 2); //WILL THIS SHOW THE CHARECTER PRESENT IN OBJECT.CHAR ?

}

If I write (POINTER+2) {technically it should mean the address of variable CHAR, because INT will take 2 bytes, so the third byte would be CHAR. But My Borland 5.02 compiler says "Illegal Structure Operation". All other statements work perfectly fine.

Recommended Answers

All 2 Replies

You can't do cout << *(POINTER + 2) for the same reason that you can't do cout << *POINTER or cout << OBJECT: There is no overload for operator << that takes an ostream and a CLASS.

Also POINTER + 2 does not add two bytes to the pointer, it adds 2 * sizeof(CLASS) bytes to the pointer. Which of course will invoke undefined behavior since there's only one object in the memory that POINTER is pointing to, not three.

commented: OK. Now I got that + 2 thing. Thanks! +1

First and foremost, identifier names that are varying case from a keyword like CLASS, INT, or CHAR, are extremely bad ideas. I strongly suggest using something more informative.

To answer your specific question, pointers to class types work exactly the same way as pointers to built-in types. For example, when you increment a pointer to a class type, it skips over the size of an object of that class rather than skipping through the members. When you say *(POINTER + 2), you're trying to access memory that you don't own just as readily as if you had an array of 1 (CLASS a[1];) and tried to execute a[2]:

#include <iostream>

namespace {
    class Foo {
    public:
        int a;
        char b;
    };
}

int main()
{
    using namespace std;

    Foo obj { 123, 'a' };
    Foo *p = &obj;

    // The same address will be printed twice
    cout << p << ' ' << &obj << '\n';

    // The same value will be printed three times
    cout << *reinterpret_cast<int*>(p) << ' ' << obj.a << ' ' << p->a << '\n';

    // Please don't do this in real code
    cout << *(reinterpret_cast<char*>(p) + sizeof(int)) << '\n';
}

cout << endl << *POINTER << " " << OBJECT.INT << " " << POINTER -> INT; //WILL THESE SHOW THE SAME?

In this exact case, yes (with an appropriate cast on *POINTER). But you should be very careful when assuming the underlying structure of a class unless it's POD. The quoted line raises all kinds of red flags for me, because it's both potentially dangerous and sign of a poorly designed solution.

But My Borland 5.02 compiler says

You should get a newer compiler. There are numerous free options, and the latest standard kind of changed the game when it comes to C++ programming style.

commented: BTW, I just used them for easy readability of my post :) And I know it is a POD. But I just wanted to understand the meaning of the statements. :) And about the compiler, I'll definitely get one after I finish my school (My education board reccomends BC4. +1
Be a part of the DaniWeb community

We're a friendly, industry-focused community of developers, IT pros, digital marketers, and technology enthusiasts meeting, networking, learning, and sharing knowledge.