Dear Gurus,
This is a fairly simple question, but I can't figure out what the answer is.
I can easily change my code, but I want to know why I can't do this to
further my knowledge of the C++ language (and OO):
class a
{
public:
a(){ vm(); }
virtual void vm() = 0;
};
class b : public a
{
public:
void vm() { }
};
int main()
{
b B;
return 0;
}
VC++ says: "error LNK2001: unresolved external symbol "public: virtual void
__thiscall a::vm(void)"
I understand that 'a' doesn't have a implementation of 'vm', but also I
cannot create an instance of 'a' either (because it has a pure virtual
function) so when I create a 'b' why can't 'a's constructor call 'b's 'vm'?
Quentin. 14 2279
On Wed, 17 Sep 2003 22:46:09 GMT, "Quentin" <IH*******@SpamSux.com> wrote: This is a fairly simple question, but I can't figure out what the answer is. I can easily change my code, but I want to know why I can't do this to further my knowledge of the C++ language (and OO):
class a { public: a(){ vm(); } virtual void vm() = 0; };
class b : public a { public: void vm() { } };
int main() { b B;
return 0; }
VC++ says: "error LNK2001: unresolved external symbol "public: virtual void __thiscall a::vm(void)"
I understand that 'a' doesn't have a implementation of 'vm', but also I cannot create an instance of 'a' either (because it has a pure virtual function) so when I create a 'b' why can't 'a's constructor call 'b's 'vm'?
This is a FAQ.
Look it up in the FAQ.
If necessary, first look up where the FAQ is (Google, this group).
Hth.,
- Alf
> Look it up in the FAQ.
Thanks Alf!
Quentin.
"Quentin" <IH*******@SpamSux.com> wrote in message
news:Ru*********************@news1.calgary.shaw.ca ... Dear Gurus,
This is a fairly simple question, but I can't figure out what the answer
is. I can easily change my code, but I want to know why I can't do this to further my knowledge of the C++ language (and OO):
class a { public: a(){ vm(); } virtual void vm() = 0; };
class b : public a { public: void vm() { } };
int main() { b B;
return 0; }
VC++ says: "error LNK2001: unresolved external symbol "public: virtual
void __thiscall a::vm(void)"
I understand that 'a' doesn't have a implementation of 'vm', but also I cannot create an instance of 'a' either (because it has a pure virtual function) so when I create a 'b' why can't 'a's constructor call 'b's
'vm'? Quentin.
Because at the time of construction of A part "this" pointer is still of
type A, hence it does not know anything about B yet. In other words,
construction starts at the top of inheritance tree, and the type of this
pointer follows. BTW, Mayers in his book Effectife C++ has a chapter about
this... you shouldn't (in most cases) call virtual functions from
constructors.
Martin
"Quentin" <IH*******@SpamSux.com> wrote in message
news:Ru*********************@news1.calgary.shaw.ca ... Dear Gurus,
This is a fairly simple question, but I can't figure out what the answer
is. I can easily change my code, but I want to know why I can't do this to further my knowledge of the C++ language (and OO):
class a { public: a(){ vm(); } virtual void vm() = 0; };
class b : public a { public: void vm() { } };
int main() { b B;
return 0; }
VC++ says: "error LNK2001: unresolved external symbol "public: virtual
void __thiscall a::vm(void)"
I understand that 'a' doesn't have a implementation of 'vm', but also I cannot create an instance of 'a' either (because it has a pure virtual function) so when I create a 'b' why can't 'a's constructor call 'b's
'vm'? Quentin.
I'm by no means a guru, and of course you can check the FAQ, but I believe
this is the problem:
Class A is an abstract base class containing an unimplemented virtual
function. Therefore, you cannot call vm() from the Class A constructor,
because in Class A it doesn't exist.
Call vm() from Class B's constructor.
Think about it... why should the compiler allow you to call Class A's vm()
if it has no function body? The compiler is doing you a favor here.
An additional question: were you to derive additional classes from A, how
would the compiler know which instance of vm() to call in A's constructor?
"Quentin" <IH*******@SpamSux.com> wrote in message
news:Ru*********************@news1.calgary.shaw.ca ... Dear Gurus,
This is a fairly simple question, but I can't figure out what the answer
is. I can easily change my code, but I want to know why I can't do this to further my knowledge of the C++ language (and OO):
class a { public: a(){ vm(); } virtual void vm() = 0; };
class b : public a { public: void vm() { } };
int main() { b B;
return 0; }
VC++ says: "error LNK2001: unresolved external symbol "public: virtual
void __thiscall a::vm(void)"
I understand that 'a' doesn't have a implementation of 'vm', but also I cannot create an instance of 'a' either (because it has a pure virtual function) so when I create a 'b' why can't 'a's constructor call 'b's
'vm'?
Whoa dude, you had it there for a minute. Now step back and think about
what you're saying. Why would a base class EVER need to know anything about
any of its subclasses? Inheritance doesn't work that way. When you create
a b, b's constructor gets called, which means a's constructor is going to
get called. But a base class function shouldn't call a subclass function.
Once you're in code for a, all it sees is a.
By the way, just because a is abstract doesn't mean you can't give a
definition for the pure virtual function. It's a common mistake to think
that though. It's often a useful technique to make a function pure virtual,
but then provide a definition that the base classes can call from their
overridden function, to do at least some common work. It might even be all
that some subclasses need to do.
"jeffc" <no****@nowhere.com> wrote in message
news:3f********@news1.prserv.net... Whoa dude, you had it there for a minute. Now step back and think about what you're saying. Why would a base class EVER need to know anything
about any of its subclasses? Inheritance doesn't work that way. When you
create a b, b's constructor gets called, which means a's constructor is going to get called. But a base class function shouldn't call a subclass function.
I was talking only about the constructor in this case, of course, not the
general case of function overriding. Constructor time is different.
> Whoa dude, you had it there for a minute. Now step back and think about what you're saying. Why would a base class EVER need to know anything
about any of its subclasses? Inheritance doesn't work that way. When you
create a b, b's constructor gets called, which means a's constructor is going to get called. But a base class function shouldn't call a subclass function. Once you're in code for a, all it sees is a.
I get it now. Whoa dude :) hahaha!
By the way, just because a is abstract doesn't mean you can't give a definition for the pure virtual function. It's a common mistake to think that though. It's often a useful technique to make a function pure
virtual, but then provide a definition that the base classes can call from their overridden function, to do at least some common work. It might even be
all that some subclasses need to do.
Whoa dude, I did not know that! That could be very useful. Thanks for the
tip!
Quentin.
"Bill Thompson" <bi*****@ixnayontheamspayrgv.rr.com> wrote in message news:<dm*******************@twister.austin.rr.com> ... "Quentin" <IH*******@SpamSux.com> wrote in message I'm by no means a guru, and of course you can check the FAQ, but I believe this is the problem: Class A is an abstract base class containing an unimplemented virtual function. Therefore, you cannot call vm() from the Class A constructor, because in Class A it doesn't exist.
Call vm() from Class B's constructor.
Think about it... why should the compiler allow you to call Class A's vm() if it has no function body? The compiler is doing you a favor here.
An additional question: were you to derive additional classes from A, how would the compiler know which instance of vm() to call in A's constructor?
Note that this is only true for calls in constructors. It's perfectly
valid to call an abstract function from any function except from
constructors and destructors (?).
BTW it is the central idea in the Template Method Pattern.
Regards,
Marcelo Pinto
"Marcelo Pinto" <mp****@tecnolink.com.br> wrote in message
news:e3**************************@posting.google.c om... "Bill Thompson" <bi*****@ixnayontheamspayrgv.rr.com> wrote in message
news:<dm*******************@twister.austin.rr.com> ... "Quentin" <IH*******@SpamSux.com> wrote in message I'm by no means a guru, and of course you can check the FAQ, but I
believe this is the problem: Class A is an abstract base class containing an unimplemented virtual function. Therefore, you cannot call vm() from the Class A constructor, because in Class A it doesn't exist.
Call vm() from Class B's constructor.
Think about it... why should the compiler allow you to call Class A's
vm() if it has no function body? The compiler is doing you a favor here.
An additional question: were you to derive additional classes from A,
how would the compiler know which instance of vm() to call in A's
constructor? Note that this is only true for calls in constructors. It's perfectly valid to call an abstract function from any function except from constructors and destructors (?).
BTW it is the central idea in the Template Method Pattern.
Regards,
Marcelo Pinto
Yes, of course, after construction the vtable has been initialized. I
should have made it more obvious I was referring to constructors, not
calling virtual functions in general.
"Quentin" <IH*******@SpamSux.com> wrote in message
news:41*********************@news1.calgary.shaw.ca ... By the way, just because a is abstract doesn't mean you can't give a definition for the pure virtual function. It's a common mistake to
think that though. It's often a useful technique to make a function pure virtual, but then provide a definition that the base classes can call from their overridden function, to do at least some common work. It might even be all that some subclasses need to do.
Whoa dude, I did not know that! That could be very useful. Thanks for
the tip!
I had a typo - I meant "provide a definition that the *subclasses* can call
from their overridden function".
Example. Program for a football game. You have football players.
class FootballPlayer
class Punter : public FootballPlayer
class DefensiveEnd : public FootballPlayer
You don't have any players on the field that are so generic that you'd
create a FootballPlayer - everyone plays a specific position. Therefore,
you make FootballPlayer abstract. But in case of crazy plays, you want
every player on the field to be able to make a tackle. You might have a
pure virtual function called Tackle() which provides some basic tackling
technique.
class FootballPlayer
{
public:
void Tackle() = 0;
};
You might override Tackle() if there is some special technique defensive
players might use. But there's nothing wrong with defining
void FootballPlayer::Tackle()
{
// tackle in some basic way
}
Then Punter could just do
void Punter::Tackle()
{
FootballPlayer::Tackle(); // the basic base function is good enough
}
The DefensiveEnd might add
void DefensiveEnd::Tackle()
{
FootballPlayer::Tackle();
// plus add a harder hit, or trying to punch the ball away on the way down
}
jeffc <no****@nowhere.com> spoke thus: You don't have any players on the field that are so generic that you'd create a FootballPlayer - everyone plays a specific position. Therefore, you make FootballPlayer abstract. But in case of crazy plays, you want every player on the field to be able to make a tackle. You might have a pure virtual function called Tackle() which provides some basic tackling technique.
class FootballPlayer { public: void Tackle() = 0; };
You might override Tackle() if there is some special technique defensive players might use. But there's nothing wrong with defining void FootballPlayer::Tackle() { // tackle in some basic way }
Then Punter could just do void Punter::Tackle() { FootballPlayer::Tackle(); // the basic base function is good enough }
Like football eh? ;) Seriously, I'm still a C++ newb, so I'm not seeing the
point of defining a pure virtual function and then overriding it. Why not
just make it a regular virtual function?
--
Christopher Benson-Manica | Jumonji giri, for honour.
ataru(at)cyberspace.org |
(blank space follows, sorry)
"Christopher Benson-Manica" <at***@nospam.cyberspace.org> wrote in message news:bk**********@chessie.cirr.com... Like football eh? ;) Seriously, I'm still a C++ newb, so I'm not seeing the point of defining a pure virtual function and then overriding it. Why not just make it a regular virtual function?
Why use function overloading, just give everything seperate names?
Because it makes sense to have the base class behavior impelemented
in a function of the same name, even if you're forced to think about
whether that is the proper behavior (by itself) in a derived class.
Ron Natalie <ro*@sensor.com> spoke thus: Why use function overloading, just give everything seperate names? Because it makes sense to have the base class behavior impelemented in a function of the same name, even if you're forced to think about whether that is the proper behavior (by itself) in a derived class.
M... (denseness/cluelessness alert!)
I thought the point of a pure virtual function was to force subclasses to
implement it, since the base class explicitly declines to do so. If the base
class wants to provide an implementation of a member function, what is
accomplished by declaring it to be purely virtual? Is it so a class that uses
classes derived from the base can choose to override the base virtual
function......?
--
Christopher Benson-Manica | Jumonji giri, for honour.
ataru(at)cyberspace.org |
"Christopher Benson-Manica" <at***@nospam.cyberspace.org> wrote in message news:bk**********@chessie.cirr.com... Ron Natalie <ro*@sensor.com> spoke thus:
Why use function overloading, just give everything seperate names? Because it makes sense to have the base class behavior impelemented in a function of the same name, even if you're forced to think about whether that is the proper behavior (by itself) in a derived class. M... (denseness/cluelessness alert!)
I thought the point of a pure virtual function was to force subclasses to implement it, since the base class explicitly declines to do so.
The first part of your statement is true, the second isn't. It forces the
derived classes (at least those who are going to be concrete) to provide
an implementation, but it doesn't say boo about whether the base class
does or not.
If the base class wants to provide an implementation of a member function, what is accomplished by declaring it to be purely virtual?
We just told you, and the football example was provided. I'll give you a more real
world one right out of our main product. Inside we have a bunch of objects that
get passed around generically. They have various functions they implement
(including such common things as the relational operators, serialize output, etc...).
Lets take the serialize function. There is a default behavior of just writing an
encoded version of the object type (which there is obtainable from the base class
via another virtual function). However, that's NOT good enough for many of
the objects. Therefore, I make the base class method pure, so that it MUST
be overridden. This forces the derived class writer to make the decision between
using the default behavior or writing a different implementation. What it doesn't
allow (and we were screwed by this a couple of times before we did this) is
to forget to put an explicit statement of the proper behavior in his class definition.
Is it so a class that uses classes derived from the base can choose to override the base virtual function......?
Well a class can always chose to override the function. What it does is force
the derived class to make an explicit statement as to whether he wants the
base behavior or something else. This thread has been closed and replies have been disabled. Please start a new discussion. Similar topics
by: AK |
last post by:
Hi all,
I have a form which simulates a form collecting a person's info for
a job. The form has the field's like fname, lname, address etc. The
last field in the form is browse for resume and...
|
by: farzad |
last post by:
Hi
I try to install php_ming.so in my php . I am using Redhat 8.0 php 4.2.2
apache 2.0.4.
I am doing as the howto install file want me to do.
as follow....
|
by: Randell D. |
last post by:
Folks,
I use Apache/PHP with Webazlier to view the log files. I get a number of
user agents (web browsers?) that visit the website - For example:
Mozilla/4.0 (compatible; MSIE 6.0; Windows NT...
|
by: Alex |
last post by:
Is it more time-consuming to troubleshoot or just start from scratch.
PHP used to work that's why I'm tempted to just re-install Linux.
|
by: @(none).dk |
last post by:
Hi
I am not sure whether my new webhotel has setup "AddType jad/jar files"
in the apache configuration file.
The webhotel has php - so my question is:
Can I make something with php that...
|
by: lawrence |
last post by:
I do get that MD5() scrambles a password, but how do you then
unscrable it? I want to get $password from the user, scrable it, then
append it to every link.
|
by: Jeffrey Silverman |
last post by:
'nuff said. Just venting...
--
Jeffrey D. Silverman | jeffrey AT jhu DOT edu
Johns Hopkins University | Baltimore, MD
Website | http://www.wse.jhu.edu/newtnotes/
|
by: paul13 |
last post by:
This seems weird, but when I use the following code,
include 'http://www.foo.com/includes.php';
includedfunction();
I am told that it is a call to an undefined function, but...
|
by: tobias |
last post by:
I am new in programming with PHP.
I wrote the following code:
file name: output.php
<?php echo $texto; ?>
And I call it on my browser like:
http://localhost/cgt/output.php?texto=testing
|
by: lawrence |
last post by:
I haven't been able to reach www.php.net for days. Most of the rest of
the web is working for me, though I've bad trouble reaching any
English sites. Anyone else having trouble?
|
by: DolphinDB |
last post by:
Tired of spending countless mintues downsampling your data? Look no further!
In this article, you’ll learn how to efficiently downsample 6.48 billion high-frequency records to 61 million...
|
by: ryjfgjl |
last post by:
ExcelToDatabase: batch import excel into database automatically...
|
by: isladogs |
last post by:
The next Access Europe meeting will be on Wednesday 6 Mar 2024 starting at 18:00 UK time (6PM UTC) and finishing at about 19:15 (7.15PM).
In this month's session, we are pleased to welcome back...
|
by: isladogs |
last post by:
The next Access Europe meeting will be on Wednesday 6 Mar 2024 starting at 18:00 UK time (6PM UTC) and finishing at about 19:15 (7.15PM).
In this month's session, we are pleased to welcome back...
|
by: ArrayDB |
last post by:
The error message I've encountered is; ERROR:root:Error generating model response: exception: access violation writing 0x0000000000005140, which seems to be indicative of an access violation...
|
by: PapaRatzi |
last post by:
Hello,
I am teaching myself MS Access forms design and Visual Basic. I've created a table to capture a list of Top 30 singles and forms to capture new entries. The final step is a form (unbound)...
|
by: Defcon1945 |
last post by:
I'm trying to learn Python using Pycharm but import shutil doesn't work
|
by: Faith0G |
last post by:
I am starting a new it consulting business and it's been a while since I setup a new website. Is wordpress still the best web based software for hosting a 5 page website? The webpages will be...
|
by: isladogs |
last post by:
The next Access Europe User Group meeting will be on Wednesday 3 Apr 2024 starting at 18:00 UK time (6PM UTC+1) and finishing by 19:30 (7.30PM).
In this session, we are pleased to welcome former...
| |