|
-
August 7th, 2007, 03:31 AM
#1
C++ protected access
This code failed to compile with both gcc and Comeau online compiler - the call to f() through a A* pointer in C::g() seems to be invalid and the call with a pointer to C it is valid, but i don't understand why. Could you explain it to me, please?
Code:
class A
{
protected:
virtual void f() {}
};
class C : public A
{
public:
void g();
};
void C::g()
{
A* pA = new C();
pA->f(); // not accessible ?
C* pC = new C();
pC->f(); // OK
}
int main()
{
}
Regards,
Cosmin
-
August 7th, 2007, 03:56 AM
#2
Re: C++ protected access
As I'm sure you are aware ...
The keyword 'protected' means that f() can only be accessed in:
* member functions of the class in which f() is defined and
* member functions of the classes derived from that class.
 Originally Posted by cosminflorea
Code:
void C::g()
{
A* pA = new C();
pA->f(); // not accessible ?
C* pC = new C();
pC->f(); // OK
}
I think it's because you are calling f() through a pointer to A, that breaks the protected contract.
-
August 7th, 2007, 04:14 AM
#3
Re: C++ protected access
 Originally Posted by Zaccheus
As I'm sure you are aware ...
* member functions of the classes derived from that class.
I think it's because you are calling f() through a pointer to A, that breaks the protected contract.
Is g() not a member function of the class derived from class A..??
SO from g() why f() is not accessible.???
-
August 7th, 2007, 04:37 AM
#4
Re: C++ protected access
 Originally Posted by code_carnage
Is g() not a member function of the class derived from class A..??
SO from g() why f() is not accessible.???
Here is my explanation (someone correct me if I'm wrong):
The variable pA has a static type of A* -- the "new C()" that is assigned to pA does not come into play when determining if a member can be accessed.
Regards,
Paul McKenzie
-
August 7th, 2007, 04:37 AM
#5
Re: C++ protected access
 Originally Posted by code_carnage
Is g() not a member function of the class derived from class A..??
SO from g() why f() is not accessible.???
Both A:f() and C::f() are protected. In C::g(), C::f() is always accessible since it is a member function of the same class. A::f() is also accessible due to the protected access. However, in the given context, the attempt is made to access A::f() not from C::g(), but within C::g(), from an A*. As such, A::f() is not accessible since it is not public.
-
August 7th, 2007, 04:38 AM
#6
Re: C++ protected access
 Originally Posted by cosminflorea
This code failed to compile with both gcc and Comeau online compiler - the call to f() through a A* pointer in C::g() seems to be invalid and the call with a pointer to C it is valid, but i don't understand why. Could you explain it to me, please?
Code:
class A
{
protected:
virtual void f() {}
};
class C : public A
{
public:
void g();
};
void C::g()
{
A* pA = new C();
pA->f(); // not accessible ?
C* pC = new C();
pC->f(); // OK
}
int main()
{
}
Change protected to public and also provide virtual destructor in the base class.
Appreciate others by rating good posts
"Only buy something that you'd be perfectly happy to hold if the market shut down for 10 years." - Warren Buffett
-
August 7th, 2007, 04:45 AM
#7
Re: C++ protected access
 Originally Posted by Zaccheus
As I'm sure you are aware ...
The keyword 'protected' means that f() can only be accessed in:
* member functions of the class in which f() is defined and
* member functions of the classes derived from that class.
Little addition
The keyword 'protected' means that f() can only be accessed in:
* member functions & friends of the class in which f() is defined and
* member functions & friends of the classes derived from that class.
Appreciate others by rating good posts
"Only buy something that you'd be perfectly happy to hold if the market shut down for 10 years." - Warren Buffett
-
August 7th, 2007, 05:12 AM
#8
Re: C++ protected access
 Originally Posted by laserlight
Both A:f() and C::f() are protected. In C::g(), C::f() is always accessible since it is a member function of the same class. A::f() is also accessible due to the protected access. However, in the given context, the attempt is made to access A::f() not from C::g(), but within C::g(), from an A*. As such, A::f() is not accessible since it is not public.
First, i thought you are right, now i found a better explanation - from the C++ standard - section 11.5
A friend or a member function of a derived class can access a protected nonstatic member of a base class. Except when forming a pointer to member, the access must be through a pointer to, reference to, or object of the derived class itself (or any class derived from that class) (5.2.4)
I still don't understand why there is such a condition...
Last edited by cosminflorea; August 7th, 2007 at 06:39 AM.
Regards,
Cosmin
-
August 7th, 2007, 05:28 AM
#9
Re: C++ protected access
 Originally Posted by laserlight
Both A:f() and C::f() are protected. In C::g(), C::f() is always accessible since it is a member function of the same class. A::f() is also accessible due to the protected access. However, in the given context, the attempt is made to access A::f() not from C::g(), but within C::g(), from an A*. As such, A::f() is not accessible since it is not public.
oooopps
-
August 7th, 2007, 07:07 AM
#10
Re: C++ protected access
 Originally Posted by cosminflorea
First, i thought you are right, now i found a better explanation - from the C++ standard - section 11.5
I still don't understand why there is such a condition...
Because you might be calling a protected member function of a class unrelated to yours except that they derive from the same parent.
The purpose of granting access is that your class knows the specifics of how this function relates to your class. But there is no reason why it should know the specifics of how this function relates to a different class that derives from the base, so it is not accessible.
-
August 7th, 2007, 07:11 AM
#11
Re: C++ protected access
There is a workaround if you really want to override that behaviour.
Code:
class A
{
public:
virtual ~A() {}
protected:
virtual void f() = 0;
virtual void call_f( A & a ) { a.f(); }
};
class B : public A
{
protected:
virtual void f(); // implement it somewhere
};
class C : public A
{
void g()
{
B b;
b.f(); // illegal
call_f( b ); // legal and will invoke b.f()
}
};
Posting Permissions
- You may not post new threads
- You may not post replies
- You may not post attachments
- You may not edit your posts
-
Forum Rules
|
Click Here to Expand Forum to Full Width
|