![]() |
![]() |
![]() |
![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() |
![]() |
![]() |
[an error occurred while processing this directive]
Steps
How It Works Let us start at the beginning of the source file. Moving past the include and using directives, the next section of code is as follows: void func1( int val ) throw( int, char* ) ; void func2( void ) throw( float ) ; void func3( void ) throw( ) ; These are, of course, function declarations. I am sure you have noticed something quite different about these declarations, namely the exception specifications. The first two exception specifications are obvious: func1() can throw only an int or a char* and function func2() can throw only a float. What exceptions will the function func3() throw? That is not so obvious. Lets think about this one: The exception specification is empty, right? That must mean this function guarantees not to throw any exceptions. The assumption proves to be correct; func3() guarantees to not throw an exception. You should be thinking about this fact whenever you are designing and coding functions and member functions. If the applications you are building utilize the exception handling facilities, you should consider marking all your functions with an exception specification. Attention to detail, although tedious, eventually pays offthe intent of your code becomes much clearer. How about functions not marked with an exception specification? Well, those functions have free rein concerning the throwing of exceptions. Quite literally, a function without an exception specification can throw any and all conceivable exceptions. It is my opinion that you are better off using exception specifications for functions that do and do not throw exceptions. The developers who will maintain your code will thank you also. As you move down through the source code, you come upon the main function. Inside main, you come upon the for loop used to call one of the three functions previously declared. The functions are called one at a time, within the try block. The section of code follows: for( int i = 0; i < 3; i++ ) { try { switch( i ) { case 0 : func1( 0 ) ; break; case 1 : func1( 1 ) ; break; case 2 : func2( ) ; break; } } For each iteration of the for loop, the try block is entered and based on the value of i, the proper case is selected within the switch. A call is made to either func1() or func2(); in both cases, an exception is thrown. In the case of func1(), an exception of type int or char* is thrown depending on the value the argument passed. Moving past the try block, you find three catch clauses. Each catch clause is designated to handle a different exception type. The catch-all catch clause could have been added to the list, but would have never realized its value because the code is handling all types of exceptions. In essence, the programs has been designed and coded for the known exceptions. In situations in which you dont know all the exceptions thrown, you should put up your guard by providing the catch-all handler. In any event, within each catch clause, a cout statement is executed to acknowledge the receipt of the exception. As you move down the source file past the main function, you find the definition for func1(). You can see that the exception specification is again specified; this is in addition to the functions declaration. The logic for the function is simple: If the value is 0, throw an int; otherwise, throw a char*. The definition for func2() is found next within the source code. Again, you see the exception specification as part of the signature. This function merely throws a float.
|
![]() |
Products | Contact Us | About Us | Privacy | Ad Info | Home
Use of this site is subject to certain Terms & Conditions, Copyright © 1996-1999 EarthWeb Inc. All rights reserved. Reproduction whole or in part in any form or medium without express written permision of EarthWeb is prohibited.
|