Calling a base-class non-virtual function which has been redefined?
I know some think I shouldn't redefine non-virtual functions from inherited classes, however, what I'm doing now is using that very role-migration concept, and it is fairly special case where it fits quite nicely.
What I want is this (oh, and this is C++):
class A {
public:
void f() { doSomethingA(); }
};
class B : public A {
public:
void f() { A::f(); doSomethingB(); }
};
However, when I do this, A::f
gets called with this == 0
, which obviously results in segfault. Am I doing something wrong, or is this simply not possible? My current option is to resort to static functions and pass the object explicitly, but I'd prefer it this way.
Yes, I could call them differently, but that kind of defeats the purpose of making them look similar to the programmer. And I can't make them virtual for various reasons (the most prominent being the role-migration, that I actually want different behavior depending on what I use it as).
Any help appreciated
开发者_如何学运维EDIT
Thank you all for answering, it appears I've stumbled upon a bug in my build environment, a minimal test case ran fine; and so did turning of optimizations. I guess I could have tried that before asking the question, but I usually assume I'm doing something wrong.Nothing more to see here, move along.. Sorry for the inconvenience... :)
Assuming that B
not inheriting from A
is a typo (I can't see this compiling otherwise), it looks like the B
pointer on which you originally call f
is null. Check the original call point, because (assuming the typo) what you wrote should work.
Your code doesn't seem to fit with the text very well. In the text, you talk about inheritance, but the code doesn't show any (and at least as-is, it shouldn't even compile).
If you do use inheritance:
class A {
public:
void f() { doSomethingA(); }
};
class B : public A {
public:
void f() { A::f(); doSomethingB(); }
};
Then when you invoke A::f()
, this
definitely should not be a NULL pointer -- it should be a valid pointer to the A
"subobject" in the B
object (as long as you use single inheritance, with most compilers it'll be the address of the object on which you invoked B::f()
, just cast from B * const
to A * const
).
Try
static_cast<A*>(this)->f()
Should work.
EDIT:
If it doesnt, check for this
in B::f()
first of all.
You didn't specify that B inherits from A:
class B : public A {
Ignoring the "correctness" of doing this, there is nothing wrong with what you're describing. I'm assuming your example code would look more like the following though to actually have the inheritance you describe:
struct A {
void f() { cout << "hi" << endl; }
};
struct B : public A {
void f() { A::f(); }
};
精彩评论