473,406 Members | 2,404 Online
Bytes | Software Development & Data Engineering Community
Post Job

Home Posts Topics Members FAQ

Join Bytes to post your question to a community of 473,406 software developers and data experts.

pure virttual function

sks

Hi ,
could anyone explain me why definition to a pure virtual function
is allowed ?

Jul 5 '06 #1
21 2524

sks wrote:
Hi ,
could anyone explain me why definition to a pure virtual function
is allowed ?
May be you are asking why it is not allowed.

See FAQ. it is better explained there.

http://www.parashift.com/c++-faq-lite/

-- Murali Krishna

Jul 5 '06 #2
"sks" <es******@gmail.comwrote in message
news:11**********************@l70g2000cwa.googlegr oups.com...
>
Hi ,
could anyone explain me why definition to a pure virtual function
is allowed ?
Yes, Herb Sutter can:

http://www.gotw.ca/gotw/031.htm

Hope this helps :)
Stu
Jul 5 '06 #3
sks
Murali Krishna wrote:
sks wrote:
Hi ,
could anyone explain me why definition to a pure virtual function
is allowed ?

May be you are asking why it is not allowed.

See FAQ. it is better explained there.

http://www.parashift.com/c++-faq-lite/

-- Murali Krishna
No , My question was why defintion to pure virtual is allowed in the
base class eg this way

class ABC
{
public:
virtual f1()=0;
{
std::cout<<"Hi";
}
}

You may derive this class and provide your own implementation to f1()
but what is the use in allowing the definition in base class?

Jul 5 '06 #4
* Murali Krishna:
*sks:
>could anyone explain me why definition to a pure virtual function
is allowed ?

May be you are asking why it is not allowed.
Sorry, the OP is correct that you can provide a definition for a pure
virtual function. But that definition can't be provided in the class
definition. As to the why of that, I don't know any good reason, and
that's better asked in [comp.std.c++].

One use for a defined pure virtual function is a "marker interface" like

struct Serializable
{
inline virtual ~Serializable() = 0;
};

inline Serializable::~Serializable() {}

Here a definition is necessary because the destructor will be called
(although it's never called virtually), and the destructor is the only
member function that for this class can be used to make it abstract.

--
A: Because it messes up the order in which people normally read text.
Q: Why is it such a bad thing?
A: Top-posting.
Q: What is the most annoying thing on usenet and in e-mail?
Jul 5 '06 #5
TB
Murali Krishna skrev:
sks wrote:
>Hi ,
could anyone explain me why definition to a pure virtual function
is allowed ?

May be you are asking why it is not allowed.
No he isn't.

class A {
public:
virtual void foo() = 0;
};

void A::foo() { }

class C : public A {
public:
void foo() {
A::foo();
}
};

int main(int argc, char* argv[])
{
C c;
c.foo();
return 0;
}
--
TB @ SWEDEN
Jul 5 '06 #6
sks

Stuart Golodetz wrote:
"sks" <es******@gmail.comwrote in message
news:11**********************@l70g2000cwa.googlegr oups.com...

Hi ,
could anyone explain me why definition to a pure virtual function
is allowed ?

Yes, Herb Sutter can:

http://www.gotw.ca/gotw/031.htm

Hope this helps :)
Stu
Thanks stuart . I have got answers to the question .

Jul 5 '06 #7
* Stuart Golodetz:
"sks" <es******@gmail.comwrote in message
news:11**********************@l70g2000cwa.googlegr oups.com...
>Hi ,
could anyone explain me why definition to a pure virtual function
is allowed ?

Yes, Herb Sutter can:

http://www.gotw.ca/gotw/031.htm

Hope this helps :)
Unfortunately reason #3 in that text is, if not exactly bu*****t, not
something one can rely on, and is with most compiler a technique that
/does not work/. Where it works -- if such a compiler exists nowadays
-- it's because Undefined Behavior can be anything, including that a
virtual call to a pure virtual function might end up in that pure
virtual function's definition. But if I could (unfortunately I can't)
I'd light a huge bonfire and throw that advice on top.

--
A: Because it messes up the order in which people normally read text.
Q: Why is it such a bad thing?
A: Top-posting.
Q: What is the most annoying thing on usenet and in e-mail?
Jul 5 '06 #8
"Alf P. Steinbach" <al***@start.nowrote in message
news:4h*************@individual.net...
>* Stuart Golodetz:
>"sks" <es******@gmail.comwrote in message
news:11**********************@l70g2000cwa.googleg roups.com...
>>Hi ,
could anyone explain me why definition to a pure virtual function
is allowed ?

Yes, Herb Sutter can:

http://www.gotw.ca/gotw/031.htm

Hope this helps :)

Unfortunately reason #3 in that text is, if not exactly bu*****t, not
something one can rely on, and is with most compiler a technique that
/does not work/. Where it works -- if such a compiler exists
nowadays -- it's because Undefined Behavior can be anything, including
that a virtual call to a pure virtual function might end up in that pure
virtual function's definition. But if I could (unfortunately I can't) I'd
light a huge bonfire and throw that advice on top.

--
A: Because it messes up the order in which people normally read text.
Q: Why is it such a bad thing?
A: Top-posting.
Q: What is the most annoying thing on usenet and in e-mail?
Hmm, my bad it would seem. Reading it again, I noticed that #2 isn't
entirely right either; it says "B::f(i)" when B::f doesn't take any
parameters. Oh well, it seemed like a good page to direct the OP to at the
time...

Apologies,
Stu
Jul 5 '06 #9
sks wrote:
Murali Krishna wrote:
sks wrote:
Hi ,
could anyone explain me why definition to a pure virtual function
is allowed ?
May be you are asking why it is not allowed.

See FAQ. it is better explained there.

http://www.parashift.com/c++-faq-lite/

-- Murali Krishna

No , My question was why defintion to pure virtual is allowed in the
base class eg this way

class ABC
{
public:
virtual f1()=0;
{
std::cout<<"Hi";
}
}

You may derive this class and provide your own implementation to f1()
but what is the use in allowing the definition in base class?
This is the first time I am seeing this and I could not believe it is
compiling. I don't know when will I open my eyes.

Murali.. come on wakeup!!

thanks for that sks.

-- Murali Krishna

Jul 5 '06 #10
Alf P. Steinbach wrote:
* Murali Krishna:
>*sks:
>>could anyone explain me why definition to a pure virtual function
is allowed ?

May be you are asking why it is not allowed.

Sorry, the OP is correct that you can provide a definition for a pure
virtual function. But that definition can't be provided in the class
definition. As to the why of that, I don't know any good reason, and
that's better asked in [comp.std.c++].

One use for a defined pure virtual function is a "marker interface" like

struct Serializable
{
inline virtual ~Serializable() = 0;
};

inline Serializable::~Serializable() {}

Here a definition is necessary because the destructor will be called
(although it's never called virtually), and the destructor is the only
member function that for this class can be used to make it abstract.
Well, if no polymorphism is needed, but the class shouldn't be
instantiatable, one can always make the destructor protected.

Jul 5 '06 #11
* Rolf Magnus:
Alf P. Steinbach wrote:
>* Murali Krishna:
>>*sks:
could anyone explain me why definition to a pure virtual function
is allowed ?
May be you are asking why it is not allowed.
Sorry, the OP is correct that you can provide a definition for a pure
virtual function. But that definition can't be provided in the class
definition. As to the why of that, I don't know any good reason, and
that's better asked in [comp.std.c++].

One use for a defined pure virtual function is a "marker interface" like

struct Serializable
{
inline virtual ~Serializable() = 0;
};

inline Serializable::~Serializable() {}

Here a definition is necessary because the destructor will be called
(although it's never called virtually), and the destructor is the only
member function that for this class can be used to make it abstract.

Well, if no polymorphism is needed, but the class shouldn't be
instantiatable, one can always make the destructor protected.
Yes, it seems that the practical advantage reduces to the single case of
a polymorphic marker interface through which objects can be deleted, but
heck, there must be more to it for having it as a langugage feature.

--
A: Because it messes up the order in which people normally read text.
Q: Why is it such a bad thing?
A: Top-posting.
Q: What is the most annoying thing on usenet and in e-mail?
Jul 5 '06 #12

Alf P. Steinbach wrote:
>
Sorry, the OP is correct that you can provide a definition for a pure
virtual function. But that definition can't be provided in the class
definition. As to the why of that, I don't know any good reason, and
that's better asked in [comp.std.c++].
because the compiler cannot understand the = 0 followed by an opening
brace?

(Maybe too hard for compiler vendors).

Jul 5 '06 #13
Earl Purple wrote:
>
Alf P. Steinbach wrote:
>>
Sorry, the OP is correct that you can provide a definition for a pure
virtual function. But that definition can't be provided in the class
definition. As to the why of that, I don't know any good reason, and
that's better asked in [comp.std.c++].

because the compiler cannot understand the = 0 followed by an opening
brace?
Seems to me rather the other way round. The compiler cannot understand it
because it's not allowed by the C++ grammar.
(Maybe too hard for compiler vendors).
Maybe I'm wrong, but this doesn't really seem to be so problematic.
Considering quite a few other parts of the C++ grammar, this seems trivial.

Jul 5 '06 #14

sks wrote:
Hi ,
could anyone explain me why definition to a pure virtual function
is allowed ?
The easiest to understand is the case for serialization frameworks. If
all classes inherit from a single class, for argument's sake Document
then you will have:

class Document {
public:
void save( ofstream & ) = 0;
void load( ifstream & ) = 0;

std::string author;
};

Derived classes must implement these members and those members must
call the Document member in order that it can save and load the
author's name. Document needs to implement both as well in order to
save and load the author's name.

This is basically an example of the occasion where the sub-class
overrides the virtual to augment the bahaviour of the super class. In
these cases the sub-class must always call the super-class
implementation as they are adding to its behaviour. Even if the upper
level implementations are empty they should still be provided so that
all sub-class implementors know that there is no reason to leave it out
and there will be no link errors when sub-classes call ones that didn't
get implement (probably 'implemented yet').
K

Jul 5 '06 #15
sks wrote:
could anyone explain me why definition to a pure virtual function
is allowed ?
The property of being 'virtual' is not as much the property of the member
function itself, as it is the property of the call method, which will be used
with that function by default in certain cases (see below). There are two
relevant call methods in this case: static (or "non-virtual") and dynamic (or
"virtual").

Dynamic (virtual) call method is used when the function is invoked by
non-qualified name with a pointer or a reference to an object. (This also
includes non-qualified calls to member functions from other member functions.
One can assume that they are implicitly prepended with 'this->...').

For example

struct S { virtual void foo() {} };
...
S s;
S* ps = &s;
S& rs = s;

ps->foo(); // virtual call
rs.foo(); // virtual call

Static (non-virtual) call method is used when the function is invoked: 1) by a
qualified name, 2) with an actual object (not a pointer or reference) 3) when
base class destructor is implicitly called from derived class destructor.

For example

ps->S::foo(); // non-virtual call
s.foo(); // non-virtual call

Now, when you declare some member function as pure virtual, you are effectively
disabling (or should I say "outlawing") the _dynamic_ (virtual) call method.
After that any attempts to invoke the function using a virtual call will lead to
either compiler diagnostic or undefined behavior. However, this has absolutely
no effect on static call methods. These calls remain perfectly valid and they
will go to the function's body (assuming it has one). If you think that it might
be useful in your program to give some member function some static call
functionality while disabling dynamic calls, then you declare it as pure virtual
and at the same time provide a definition (a body) for it.

--
Best regards,
Andrey Tarasevich
Jul 5 '06 #16
* Andrey Tarasevich:
>
Static (non-virtual) call method is used when the function is invoked: 1) by a
qualified name, 2) with an actual object (not a pointer or reference) 3) when
base class destructor is implicitly called from derived class destructor.
Accepting this terminology, point (2) does not apply to a call to a pure
virtual function from a non-static member function of the class (where
you can very easily have UB if that member function is directly or
indirectly called from a constructor of the class), and it does not
apply to a call on a named variable of the class, since no such variable
can exist if the class has a pure virtual function; hence it doesn't
seem to apply to anything in this context, and for the case of a call of
function that's not pure virtual, it's an implementation detail that
only affects the efficiency of a call, if anything, so at the C++ level
it doesn't make much sense to say if that call is virtual or not.

--
A: Because it messes up the order in which people normally read text.
Q: Why is it such a bad thing?
A: Top-posting.
Q: What is the most annoying thing on usenet and in e-mail?
Jul 5 '06 #17
Alf P. Steinbach wrote:
>>
Static (non-virtual) call method is used when the function is invoked: 1) by a
qualified name, 2) with an actual object (not a pointer or reference) 3) when
base class destructor is implicitly called from derived class destructor.

Accepting this terminology,
If you are referring to the above use of terms "static" and "dynamic", I agree
that they are a bit ambiguous, since similar terms are used elsewhere in the
language, where they mean something completely different. However, this is not
entirely my invention. This terminology is derived directly from the one used in
the FAQ, see

http://www.parashift.com/c++-faq-lit....html#faq-20.2
http://www.parashift.com/c++-faq-lit....html#faq-20.3
point (2) does not apply to a call to a pure
virtual function from a non-static member function of the class (where
you can very easily have UB if that member function is directly or
indirectly called from a constructor of the class),
I'd say that this is more relevant to point (1), i.e. what I referred to as
"call by a qualified name".
and it does not
apply to a call on a named variable of the class, since no such variable
can exist if the class has a pure virtual function;
That would be point (2), yes.
hence it doesn't
seem to apply to anything in this context, and for the case of a call of
function that's not pure virtual, it's an implementation detail that
only affects the efficiency of a call, if anything, so at the C++ level
it doesn't make much sense to say if that call is virtual or not.
I don't understand what exactly you are referring to by the "implementation
detail" part, since I don't see anything in my post that would be an
implementation detail.

Anyway, my description was not intended to be limited to the particular case of
_pure_ virtual functions. It was supposed to be more generic, with only the last
paragraph of my original message dealing with pure virtual functions in particular.

--
Best regards,
Andrey Tarasevich
Jul 5 '06 #18
sks wrote:
Hi ,
could anyone explain me why definition to a pure virtual function
is allowed ?
See "Effective C++, 3Ed", Item 34 for an example.
Jul 5 '06 #19
* Andrey Tarasevich:
Alf P. Steinbach wrote:
>>Static (non-virtual) call method is used when the function is invoked: 1) by a
qualified name, 2) with an actual object (not a pointer or reference) 3) when
base class destructor is implicitly called from derived class destructor.
Accepting this terminology,

If you are referring to the above use of terms "static" and "dynamic", I agree
that they are a bit ambiguous, since similar terms are used elsewhere in the
language, where they mean something completely different. However, this is not
entirely my invention. This terminology is derived directly from the one used in
the FAQ, see

http://www.parashift.com/c++-faq-lit....html#faq-20.2
http://www.parashift.com/c++-faq-lit....html#faq-20.3
>point (2) does not apply to a call to a pure
virtual function from a non-static member function of the class (where
you can very easily have UB if that member function is directly or
indirectly called from a constructor of the class),

I'd say that this is more relevant to point (1), i.e. what I referred to as
"call by a qualified name".
No, I mean an unqualified call, like

struct Oops
{
Oops() { g(); } // <-- Call of pure virtual function
virtual void g() = 0;
};

void Oops::g() {}

For any quality compiler you're guaranteed that the code fails to
compile or else that the call g() is implemented as a virtual call (then
resulting in a call of a function that issues a run-time diagnostic), in
spite of the dynamic type of the object being known.

This does not contradict what you wrote, it just sensibly narrows the
(lacking) definition of "actual object" in point 2, namely, that it does
not include this case, or any case where g() is called unqualified from
a non-static member function of Oops.

>and it does not
apply to a call on a named variable of the class, since no such variable
can exist if the class has a pure virtual function;

That would be point (2), yes.
>hence it doesn't
seem to apply to anything in this context, and for the case of a call of
function that's not pure virtual, it's an implementation detail that
only affects the efficiency of a call, if anything, so at the C++ level
it doesn't make much sense to say if that call is virtual or not.

I don't understand what exactly you are referring to by the "implementation
detail" part, since I don't see anything in my post that would be an
implementation detail.
It means that the compiler may choose to implement the call below,

struct Foo { virtual void bar() {} };

int main() { Foo().bar(); }

as a virtual call or as a statically bound call, at its discretion, and
the only way you'll ever know would be by inspecting the machine code.

So I contend that point 2 is not actually meaningful as description of
what happens in practice, because it doesn't apply in any concrete case
I can think of, and AFAIK it does not describe a requirement by the
standard -- I'd leave it out entirely, because a reader will try to
ascribe some meaning that matters, which would likely be incorrect.

Anyway, my description was not intended to be limited to the particular case of
_pure_ virtual functions. It was supposed to be more generic, with only the last
paragraph of my original message dealing with pure virtual functions in particular.
--
A: Because it messes up the order in which people normally read text.
Q: Why is it such a bad thing?
A: Top-posting.
Q: What is the most annoying thing on usenet and in e-mail?
Jul 5 '06 #20
* Alf P. Steinbach:
>
struct Oops
{
Oops() { g(); } // <-- Call of pure virtual function
virtual void g() = 0;
};

void Oops::g() {}

For any quality compiler you're guaranteed that the code fails to
compile or else that the call g() is implemented as a virtual call (then
resulting in a call of a function that issues a run-time diagnostic), in
spite of the dynamic type of the object being known.
Except MSVC 7.1... :-(

g++ refuses to compile the code, Comeau warns, MSVC 7.1 happily compiles
it with no diagnostic (!) and calls the Oops::g() implementation.

Did I just say that MSVC 7.1 is not a quality compiler? Seems so.
Since I've maintained the opposite on numerous occasions I have hereby
contradicted myself -- what would life be without contradictions?

--
A: Because it messes up the order in which people normally read text.
Q: Why is it such a bad thing?
A: Top-posting.
Q: What is the most annoying thing on usenet and in e-mail?
Jul 5 '06 #21
Alf P. Steinbach wrote:
>...
I don't understand what exactly you are referring to by the "implementation
detail" part, since I don't see anything in my post that would be an
implementation detail.

It means that the compiler may choose to implement the call below,

struct Foo { virtual void bar() {} };

int main() { Foo().bar(); }

as a virtual call or as a statically bound call, at its discretion, and
the only way you'll ever know would be by inspecting the machine code.
Well, the only distinction between the two methods of invoking a function I was
trying to describe in my message is the distinction explicitly mentioned in the
language specification: what I referred to as "dynamic call" is a call that is
resolved in accordance with the _dynamic_ type of the object expression (which
is the standard terminology), while "static calls" are resolved in accordance
with static type of the object expression. This distinction does exist at
conceptual level, i.e. it is specified in the language standard and it does
apply to point (2), as it applies to all other points.

Since you mention the machine code (and taking into account the example above),
you apparently are talking about significantly more lower-level details relevant
to more-or-less "traditional" implementations of the virtual call mechanism. I,
on the other hand, was not trying to get such low-level details involved.

--
Best regards,
Andrey Tarasevich
Jul 5 '06 #22

This thread has been closed and replies have been disabled. Please start a new discussion.

Similar topics

11
by: santosh | last post by:
Hello, I was going through the Marshal Cline's C++ FAQ-Lite. I have a doubt regarding section 33.10. Here he is declaring a pure virtual destructor in the base class. And again defining...
6
by: pakis | last post by:
I am having a problem of pure virtual function call in my project. Can anyone explaine me the causes of pure virtual function calls other than calling a virtual function in base class? Thanks
10
by: John Goche | last post by:
Hello, page 202 of Symbian OS Explained by Jo Stichbury states "All virtual functions, public, protected or private, should be exported" then page 203 states "In the rare cases where a...
2
by: ChrisO | last post by:
I've been pretty infatuated with JSON for some time now since "discovering" it a while back. (It's been there all along in JavaScript, but it was just never "noticed" or used by most until...
10
by: Rahul | last post by:
Hi, I tried to create a abstract class by having a non-virtual member function as pure, but i got a compilation error saying "only virtual member functions can be pure"... I'm trying to think...
14
by: Jack | last post by:
Hi, I meet a question with it , I did not get clear the different betteen them, for example: #include <iostream>
0
by: emmanuelkatto | last post by:
Hi All, I am Emmanuel katto from Uganda. I want to ask what challenges you've faced while migrating a website to cloud. Please let me know. Thanks! Emmanuel
1
by: nemocccc | last post by:
hello, everyone, I want to develop a software for my android phone for daily needs, any suggestions?
1
by: Sonnysonu | last post by:
This is the data of csv file 1 2 3 1 2 3 1 2 3 1 2 3 2 3 2 3 3 the lengths should be different i have to store the data by column-wise with in the specific length. suppose the i have to...
0
by: Hystou | last post by:
There are some requirements for setting up RAID: 1. The motherboard and BIOS support RAID configuration. 2. The motherboard has 2 or more available SATA protocol SSD/HDD slots (including MSATA, M.2...
0
by: Hystou | last post by:
Most computers default to English, but sometimes we require a different language, especially when relocating. Forgot to request a specific language before your computer shipped? No problem! You can...
0
Oralloy
by: Oralloy | last post by:
Hello folks, I am unable to find appropriate documentation on the type promotion of bit-fields when using the generalised comparison operator "<=>". The problem is that using the GNU compilers,...
0
jinu1996
by: jinu1996 | last post by:
In today's digital age, having a compelling online presence is paramount for businesses aiming to thrive in a competitive landscape. At the heart of this digital strategy lies an intricately woven...
0
tracyyun
by: tracyyun | last post by:
Dear forum friends, With the development of smart home technology, a variety of wireless communication protocols have appeared on the market, such as Zigbee, Z-Wave, Wi-Fi, Bluetooth, etc. Each...
0
agi2029
by: agi2029 | last post by:
Let's talk about the concept of autonomous AI software engineers and no-code agents. These AIs are designed to manage the entire lifecycle of a software development project—planning, coding, testing,...

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.