  | 
   A New Cast For C++, With Rating 
   Submitted by  |   
  
  
Following my previous TOTD thread, I began thinking about what I think are 
the most important things you need to consider when you're about to 
implement a technique using something "really smart", especially in C++:
  1- The ease of use of the technique. If it's hard to use, it won't be used.
  2- The ease of understanding how it works, black-box style. If its 
functioning is obscure, users will make too many mistakes.
  3- The clarity of error messages when users do make mistakes, typos, etc...
  4- The ease, for you, of understanding the innards of the technique. If you 
came, say, a year later, and you had to mess with it, how bad would it be?
  5- The ease, for another programmer, of understanding the innards. In case 
you jump from a plane and forget the parachute, so to speak.
  (Am I forgetting anything critical here?)
  I believe that, with those things, you can measure the desirability of 
actually doing it. It should be interesting if we start rating our posts 
like that.
  Anyway, I'd like to post a nice tip. It's not from me, originally. I saw it 
in a presentation by one of the developers at Microsoft working on the 
MSVC++ debugger, so the actual credit should go to him. I just don't 
remember his name. He proposed a new cast, called checked_cast. It would 
work just as a static_cast, except that it would use dynamic_cast to catch 
programming errors in debug mode. I modified it somewhat, so it ended up 
like this:
  
template < class TypeTo, class TypeFrom 
__forceinline TypeTo checked_cast(TypeFrom *t) {
#if (defined(CHECKED_BUILD) || !defined(NDEBUG))
   if (t) {
     TypeTo dtto = dynamic_cast<TypeTo(t);
     TypeTo stto = static_cast<TypeTo(t);
     ASSERT(dtto != 0);
     ASSERT(dtto == stto);
     return stto;
   } else {
     return 0;
   }
#else
   return static_cast<TypeTo(t);
#endif
}  |  
 
  
If you try to perform an up-cast with checked_cast when in debug mode, 
it'll assert out. In release mode, it'll assume the cast is correct, and so 
it performs it in the most efficient manner.
  So... how should we rate this? My personal opinion is:
 
 
1- Very good.
2- Very good.
3- Very good (MSVC).
4- Very good. (That's for me ;-)
5- Good, I believe. It does require some understanding of templates, though.
 
  To test the error message generation I used the following code in MSVC++ 6.0:
  
struct A {};
struct B: A {};
  void func2()
{
   static_cast(8);
   checked_cast(8);
   static_cast<2;
   checked_cast<2;
   static_cast<2();
   checked_cast<2();
     A a;
   B *pb;
     pb = static_cast<A*(&a);
   pb = checked_cast<A*(&a);
     pb = static_cast<int*(&a);
   pb = checked_cast<int*(&a);
     pb = static_cast<int(&a);
   pb = checked_cast<int(&a);
     pb = static_cast<B(&a);
   pb = checked_cast<B(&a);
     // Correct form.
   pb = static_cast<B*(&a);
   pb = checked_cast<B*(&a);
}  |  
 
  
In all cases the message was marked on the proper line of code, and, in all 
the cases after defining the local variables, I got for static_cast the 
same error message that I got for checked_cast.
  Salutaciones, 
      
                               JCAB
 | 
 
 
 
The zip file viewer built into the Developer Toolbox made use
of the zlib library, as well as the zlibdll source additions.
 
 
 |