Reputation: 3
Can any one explain what does it mean by making an pointer to an object to NULL?
When we assign ptr to an object to NULL, how can we still access the member function?
class A
{
public:
void print()
{
cout<<"Hello";
}
}
int main()
{
A * a;
A* b = NULL;
a->print();
b->print();
}
EDIT: Will the program crash? http://ideone.com/DudZ6
Upvotes: 0
Views: 132
Reputation: 154047
You can't. Any attempt to dereference the pointer (any application of
the *
or ->
operator to it) is undefined behavior, and may do
anything. Most of the time, of course, you'll only crash if the
code actually needs data from the object (including internal data like a
vptr
); otherwise, the code will seem to work. But that's just one of
the possible undefined behaviors; I've actually used a compiler where
your small program would crash.
As per C++ Standard:
1.9 Program execution
4:
Certain other operations are described in this International Standard as undefined (for example, the effect of dereferencing the null pointer). [Note: this International Standard imposes no requirements on the behavior of programs that contain undefined behavior. ]
So strictly, speaking the behavior is undefined, As many have pointed out in comments section just because it works on a particular platform does not make it legal.
So the as per the C++ standard the behavior of the code snippet is Undefined Behavior.
Upvotes: 5
Reputation: 7302
The pointer is used for accessing the members of that object. If your function(s) don't need to access any members and are not virtual, they actually don't use the object. The code is still strictly speaking invalid, but it won't crash.
If you replace the contents with printing the "this" pointer, it'll still work as you're not dereferencing it.
struct X {
void print() {
cout << "this pointer is " << this << endl;
}
};
int main() {
X *x;
x->print(); // will print whatever was on the stack, ie, random garbage
X *t = NULL;
t->print(); // will print a null pointer
}
If you add one member variable and print that, or make the function virtual (so it will have to be looked up through the object itself) it will crash.
struct X {
virtual void print() {
cout << "Hello World" << endl;
}
};
struct X2 {
int y;
void print() {
cout << "y is " << y << endl;
}
};
int main() {
X *x = NULL;
x->print(); // will crash on null pointer dereference
X2 *x2 = NULL;
x2->print(); // will crash on null pointer dereference
}
Upvotes: 5
Reputation: 69047
You can't,
A* b = NULL;
b->print();
this is undefined bahvior and could make your program crash with a segmentation fault (depending on the definition of your print
method).
Generally speaking, assigning NULL to a pointer is used to give the pointer a value that means "this pointer is not set, do not use it". Take this code:
void function() {
int* p;
int* q = NULL:
...
}
when the function is called, p
and q
are allocated on the stack; due to the way compiler works, p
is left unassigned, that means that it gets the value that it is found on the stack at the moment of calling the function; this is a random value that usually has not much to do with your program.
Now, the fact that p
has got a value could lead you into thinking that this value is "correct", so you use it; but, it is not (because it is random, due to not initializing the pointer), so you also get a crash or some kind of unexpected behavior.
In the case of q
, the fact of assigning NULL
to it allows you to tell that it has no usable value. So, you don't reference it:
if (q != NULL) {
q->....
}
The idiom above does not work for p
, so you have no way to tell whether it is ok.
In the end: always initialize your variable; in the case of pointers, if you do not have a vlaue to assign, assign NULL, so you know that pointer should not be dereferenced.
Upvotes: 1