472,951 Members | 1,815 Online
Bytes | Software Development & Data Engineering Community
Post Job

Home Posts Topics Members FAQ

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

about dynamic_cast<>()

Hi, there !

When I use dynamic_cast for a single object, I do something like:

void foo(Base *base)
{
if ( dynamic_cast<Derived *>( base ) != NULL ) {
((Derived *) base)->do_something()
}
}

I know it's better to avoid abuse of dynamic_cast, user virtual
functions, and so on.

However, I think it would be more practical to be able to write
something like:
if ( istypeof<Derived>( base ) ) {
}

I find the dynamic_cast style (actually, all '*_cast<>"), to take too
much characters to be written, and this is specially annoying in
formatting, for example.

Is there somehting like this within the proposals for the new
standard ?
(or maybe there is already something like this in the current
standard)

Regards,

Baltasar
Nov 29 '07 #1
13 2075
ba*******@gmail.com wrote:
When I use dynamic_cast for a single object, I do something like:

void foo(Base *base)
{
if ( dynamic_cast<Derived *>( base ) != NULL ) {
((Derived *) base)->do_something()
}
A better (idiomatic) way would be

if (Derived *derived = dynamic_cast<Derived*>(base)) {
derived->do_something();
}

Of course the best way would be to have 'do_something' declared
'virtual' and overridden in 'Derived', so that you don't need to
find out what real type the object was. You'd just write

base->do_something();
}

I know it's better to avoid abuse of dynamic_cast, user virtual
functions, and so on.
Oh... Good. So you probably also know the usual joke mentioned in
such a situation:

Patient: "Doctor, if I do *this*, it hurts."
Doctor: "Don't do that."
However, I think it would be more practical to be able to write
something like:
if ( istypeof<Derived>( base ) ) {
}
....and then what? And how is it more practical?
I find the dynamic_cast style (actually, all '*_cast<>"), to take too
much characters to be written, and this is specially annoying in
formatting, for example.
So, you're trying to avoid carpal tunnel syndrome, is that it?

As you say, if you abuse 'dynamic_cast' or for some reason design
your classes wrong, you will be stuck with much more typing. Just
imagine that 'do_something' is virtual. What a pleasure it is to
simply omit all the 'if' and 'dynamic_cast' and such...
Is there somehting like this within the proposals for the new
standard ?
Nope.
(or maybe there is already something like this in the current
standard)
Nope.

V
--
Please remove capital 'A's when replying by e-mail
I do not respond to top-posted replies, please don't ask
Nov 29 '07 #2
ba*******@gmail.com wrote:
Hi, there !

When I use dynamic_cast for a single object, I do something like:

void foo(Base *base)
{
if ( dynamic_cast<Derived *>( base ) != NULL ) {
((Derived *) base)->do_something()
}
}

I know it's better to avoid abuse of dynamic_cast, user virtual
functions, and so on.

However, I think it would be more practical to be able to write
something like:
if ( istypeof<Derived>( base ) ) {
}

I find the dynamic_cast style (actually, all '*_cast<>"), to take too
much characters to be written, and this is specially annoying in
formatting, for example.
How much of a different does it make when you type "if
(istypeof<Derived>(base))" instead of "if (dynamic_cast<Derived*>(base))"? You
only saved 5 characters! I think that one of the best things that could happen
to the software industry is the automatic complition feature of modern compilers
(it made code much more readable). Why don't you use this feature?

BTW, in your examples, you have to cast the pointer twice: once for checking the
if-condition, and once for actually using the casted pointer. That is not how it
is intended to be (a proper code checking tool would complain about the C-style
cast, anyway). Your code should look like this:

void foo(Base *base)
{
Derived* derived = dynamic_cast<Derived *>( base );
if ( derived ) {
derived->do_something();
}
}

or if you are someone who doesn't want to type too much:

void foo(Base *base)
{
if ( Derived* derived = dynamic_cast<Derived *>( base )) {
derived->do_something();
}
}

Regards,
Stuart
Nov 29 '07 #3
ba*******@gmail.com wrote:
Hi, there !

When I use dynamic_cast for a single object, I do something like:

void foo(Base *base)
{
if ( dynamic_cast<Derived *>( base ) != NULL ) {
((Derived *) base)->do_something()
}
}
Why the C-style cast? I would prefer

void foo ( Base* base ) {
Derived* ptr = dynamic_cast< Derived* >( base );
if ( ptr != 0 ) {
ptr->do_something();
}
}

In think, you could even do this:

void foo ( Base* base ) {
if ( Derived* ptr = dynamic_cast< Derived* >( base ) ) {
ptr->do_something();
}
}

I know it's better to avoid abuse of dynamic_cast, user virtual
functions, and so on.

However, I think it would be more practical to be able to write
something like:
if ( istypeof<Derived>( base ) ) {
}

I find the dynamic_cast style (actually, all '*_cast<>"), to take too
much characters to be written, and this is specially annoying in
formatting, for example.
That, I think, is intentional: the casts stick and look ugly so that they
are not taken lightly.

Moreover, you can easily implement that istypeof() function yourself. So
what's stoping you?

Is there somehting like this within the proposals for the new
standard ?
I sure don't hope so, and I am not aware of anything.
(or maybe there is already something like this in the current
standard)
Nothing that I was aware of.
Best

Kai-Uwe Bux
Nov 29 '07 #4
ba*******@gmail.com wrote:
I find [...] to take too much characters to be written
That has *never* been a good principle in programming. It's, IMO, a
very common beginner mistake (ie. to try to minimize writing effort).
Nov 29 '07 #5
ba*******@gmail.com wrote:
I find the dynamic_cast style (actually, all '*_cast<>"), to take too
much characters to be written, and this is specially annoying in
formatting, for example.
You could use something like:

#define with_type(ty, x, y) \
if (ty x = dynamic_cast<ty>(y))
Don't know if that would be more to your taste.
Simple example follows:

----------------------------------------------------------------------
#include <iostream>

#define with_type(ty, x, y) \
if (ty x = dynamic_cast<ty>(y))

struct bar {
int x;
bar(int x_ = 0): x(x_) {}
virtual ~bar() {}
};

struct foo: public bar {
};

int main()
{
bar *a = new foo;

with_type(foo*, b, a) {
std::cout << b->x << '\n';
}

return 0;
}
----------------------------------------------------------------------

(Yes, I'm a Lispnik.)
Nov 29 '07 #6
Juha Nieminen wrote:
That has *never* been a good principle in programming. It's, IMO, a
very common beginner mistake (ie. to try to minimize writing effort).
Concise code is usually more readable (unless it degenerates into
p***-style linenoise).
Nov 29 '07 #7
On 2007-11-29 08:24:52 -0500, Kai-Uwe Bux <jk********@gmx.netsaid:
ba*******@gmail.com wrote:
>Hi, there !

When I use dynamic_cast for a single object, I do something like:

void foo(Base *base)
{
if ( dynamic_cast<Derived *>( base ) != NULL ) {
((Derived *) base)->do_something()
}
}

Why the C-style cast? I would prefer

void foo ( Base* base ) {
Derived* ptr = dynamic_cast< Derived* >( base );
if ( ptr != 0 ) {
ptr->do_something();
}
}

In think, you could even do this:

void foo ( Base* base ) {
if ( Derived* ptr = dynamic_cast< Derived* >( base ) ) {
ptr->do_something();
}
}
Just to emphasize: the C-style cast can produce the wrong result. For
example, if Base is a virtual base of Derived, dynamic_cast produces
the correct pointer value and the C-style cast is simply wrong. So
either of these code examples would be much better than the original
version. And the second of these two is the motivating example for
allowing declarations in conditionals. It restricts the scope of ptr to
the block controlled by the if statement.

--
Pete
Roundhouse Consulting, Ltd. (www.versatilecoding.com) Author of "The
Standard C++ Library Extensions: a Tutorial and Reference
(www.petebecker.com/tr1book)

Nov 29 '07 #8
On Nov 29, 1:18 pm, "Victor Bazarov" <v.Abaza...@comAcast.netwrote:
baltas...@gmail.com wrote:
When I use dynamic_cast for a single object, I do something like:
void foo(Base *base)
{
if ( dynamic_cast<Derived *>( base ) != NULL ) {
((Derived *) base)->do_something()
}

A better (idiomatic) way would be

if (Derived *derived = dynamic_cast<Derived*>(base)) {
derived->do_something();
}
Indeed. To the OP, the rationale behind the use of
dynamic_cast in the idiomatic way that Victor illustrates,
as opposed to the language providing some sort of istypeof
operator, is to allow the test ("is base of type Derived* ?")
and the conversion ("alright then, give me it as a Derived*")
to happen in a single statement. This is not only more elegant,
it is less error-prone, and something that I sorely miss when
labouring in Java, VB.NET and their ilk.
Nov 29 '07 #9

Hi again !

Thank you all for your [funny] answers.
Moreover, you can easily implement that istypeof() function yourself. So
what's stopping you?
Prudence.

Regards,

Baltasar
Nov 29 '07 #10
On Nov 29, 2:58 pm, Matthias Buelow <m...@incubus.dewrote:
Juha Nieminen wrote:
That has *never* been a good principle in programming. It's, IMO, a
very common beginner mistake (ie. to try to minimize writing effort).
Concise code is usually more readable (unless it degenerates into
p***-style linenoise).
It depends. Replacing all of your variable names with one or
two character names will NOT improve readability. Exotic
overuse of complex expressions will not improve readability.
Avoiding named variables in favor of overly complex flow control
(break or return in the middle of a loop, for example) will not
improve readability.
--
James Kanze (GABI Software) email:ja*********@gmail.com
Conseils en informatique orientée objet/
Beratung in objektorientierter Datenverarbeitung
9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34
Nov 30 '07 #11
On 2007-11-30 04:01:07 -0500, James Kanze <ja*********@gmail.comsaid:
On Nov 29, 2:58 pm, Matthias Buelow <m...@incubus.dewrote:
>Juha Nieminen wrote:
>>That has *never* been a good principle in programming. It's, IMO, a
very common beginner mistake (ie. to try to minimize writing effort).
>Concise code is usually more readable (unless it degenerates into
p***-style linenoise).

It depends. Replacing all of your variable names with one or
two character names will NOT improve readability.
It depends on what the names were to begin with. It's hard to
distinguish at a glance between long names that differ by only a few
characters, because the differences are lost in the noise. Short names
don't have so much noise. And, of course, the code that uses them
doesn't run off the edge of the screen. <g>

--
Pete
Roundhouse Consulting, Ltd. (www.versatilecoding.com) Author of "The
Standard C++ Library Extensions: a Tutorial and Reference
(www.petebecker.com/tr1book)

Nov 30 '07 #12
Matthias Buelow wrote:
Juha Nieminen wrote:
> That has *never* been a good principle in programming. It's, IMO, a
very common beginner mistake (ie. to try to minimize writing effort).

Concise code is usually more readable
It depends on what you mean by "concise code".

There's a difference between an algorithm which has been cleanly
implemented in a concise way, and using artificially concise code (eg.
short variable names) just to save typing.

The former, when well done, can indeed improve readability. The latter
usually degrades it. Artificially shortening code just to save typing,
for no other good reason, does not make the code easier to read, but all
the contrary. Usually it makes the code more obfuscated.
Nov 30 '07 #13
Pete Becker wrote:
On 2007-11-30 04:01:07 -0500, James Kanze <ja*********@gmail.comsaid:
On Nov 29, 2:58 pm, Matthias Buelow <m...@incubus.dewrote:
Juha Nieminen wrote:
That has *never* been a good principle in programming. It's, IMO, a
very common beginner mistake (ie. to try to minimize writing effort).
Concise code is usually more readable (unless it degenerates into
p***-style linenoise).
It depends. Replacing all of your variable names with one or
two character names will NOT improve readability.
It depends on what the names were to begin with. It's hard to
distinguish at a glance between long names that differ by only a few
characters, because the differences are lost in the noise. Short names
don't have so much noise. And, of course, the code that uses them
doesn't run off the edge of the screen. <g>
I was, of course, talking in general. Replacing all of the
names in a program with a1, a2, ... etc. is a classical
obfuscation trick. Of course, for obfuscation, replacing them
all with twenty character long names randomly generated using
only O, 0, l and 1 is even better (and don't forget to write 0
and 1 00000000000000000000 and 000000000000001---not to be
confused with O0000000000000000000 and O00000000000001).

And of course, for things like local index variables, anything
but i, j, k... is obfuscation.

If you take well written code, however, and force all of the
names down to 2 characters, you will definitely end up with
shorter code, but it will be significantly less readable.

--
James Kanze (GABI Software) email:ja*********@gmail.com
Conseils en informatique orientée objet/
Beratung in objektorientierter Datenverarbeitung
9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34
Nov 30 '07 #14

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

Similar topics

3
by: alg | last post by:
dynamic_cast<> comes in play when to perform conversion from a pointer to a base class to a pointer to a derived class. I don't understand: 1. why this is so necessary since we can either use...
11
by: Jamie Burns | last post by:
Hello, I just did a simple benchmark: for (xx=0;xx<100000;xx++) { rDerived* derived = dynamic_cast<rDerived*>(object); if (derived) derived->setValue(message.data.messageSetInt.value); } ...
15
by: Grizlyk | last post by:
Hello. Returning to question of manual class type identification, tell me, for ordinary inheritance is C++ garantee that dynamic_cast<Derived*>(Base*) can be implemented similarly to ...
2
isladogs
by: isladogs | last post by:
The next Access Europe meeting will be on Wednesday 4 Oct 2023 starting at 18:00 UK time (6PM UTC+1) and finishing at about 19:15 (7.15PM) The start time is equivalent to 19:00 (7PM) in Central...
0
by: Aliciasmith | last post by:
In an age dominated by smartphones, having a mobile app for your business is no longer an option; it's a necessity. Whether you're a startup or an established enterprise, finding the right mobile app...
0
tracyyun
by: tracyyun | last post by:
Hello everyone, I have a question and would like some advice on network connectivity. I have one computer connected to my router via WiFi, but I have two other computers that I want to be able to...
2
by: giovanniandrean | last post by:
The energy model is structured as follows and uses excel sheets to give input data: 1-Utility.py contains all the functions needed to calculate the variables and other minor things (mentions...
4
NeoPa
by: NeoPa | last post by:
Hello everyone. I find myself stuck trying to find the VBA way to get Access to create a PDF of the currently-selected (and open) object (Form or Report). I know it can be done by selecting :...
3
NeoPa
by: NeoPa | last post by:
Introduction For this article I'll be using a very simple database which has Form (clsForm) & Report (clsReport) classes that simply handle making the calling Form invisible until the Form, or all...
1
by: Teri B | last post by:
Hi, I have created a sub-form Roles. In my course form the user selects the roles assigned to the course. 0ne-to-many. One course many roles. Then I created a report based on the Course form and...
3
by: nia12 | last post by:
Hi there, I am very new to Access so apologies if any of this is obvious/not clear. I am creating a data collection tool for health care employees to complete. It consists of a number of...
0
NeoPa
by: NeoPa | last post by:
Introduction For this article I'll be focusing on the Report (clsReport) class. This simply handles making the calling Form invisible until all of the Reports opened by it have been closed, when it...

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.