1 / 41

NKU CSC 601 Fall 2002 K. Kirby

Exceptions. NKU CSC 601 Fall 2002 K. Kirby. This week’s readings Stroustrup Chapter 10. Classes Chapter 12. Derived classes Chapter 14. Exception handing. TODAY. NKU CSC 601 Fall 2002 K. Kirby. What’s an error?. What can you do with errors? Let an assertion fail?

gianna
Download Presentation

NKU CSC 601 Fall 2002 K. Kirby

An Image/Link below is provided (as is) to download presentation Download Policy: Content on the Website is provided to you AS IS for your information and personal use and may not be sold / licensed / shared on other websites without getting consent from its author. Content is provided to you AS IS for your information and personal use only. Download presentation by click this link. While downloading, if for some reason you are not able to download a presentation, the publisher may have deleted the file from their server. During download, if you can't get a presentation, the file might be deleted by the publisher.

E N D

Presentation Transcript


  1. Exceptions NKU CSC 601 Fall 2002 K. Kirby

  2. This week’s readings Stroustrup Chapter 10. Classes Chapter 12. Derivedclasses Chapter 14. Exception handing TODAY NKU CSC 601 Fall 2002 K. Kirby

  3. What’s an error? • What can you do with errors? • Let an assertion fail? • Use assertions only as comments with runtime force. For cases that should never fail. A way to comment on pre-/post- conditions and invariants. • Write error message and prompt? and quit?Write it where? (Is there a console?) Can we just quit without knowing the context?! • Return error code?Well, COM does it. But it’s ridiculous to force programmers to check each call. • Leave object in error state? • Not bad, but too ad hoc. • Throw an exceptionYes. We can respond when and where we care, but without discarding information. NKU CSC 601 Fall 2002 K. Kirby

  4. Exception Issues Throwing and catching Specifications Standard exceptions Resource control NKU CSC 601 Fall 2002 K. Kirby

  5. Throwing is easy. void f() { cout << “Enter a positive number” ; cin >> n ; if ( n < 0 ) ; throw “a tantrum” ; // .. etc. } No “Throwable” class like Java. Throw anything! NKU CSC 601 Fall 2002 K. Kirby

  6. Catching is easy too. void something() { try { // ... etc. f() ; // ... etc . } catch ( const char* s ) { cerr << “Caught:” << s << endl ; } } NKU CSC 601 Fall 2002 K. Kirby

  7. What To Throw Best to throw objects of type exception (in <exception>). Even better to throw a standard one (in <stdexcept>). #include <stdexcept> void f() { cout << “Enter a positive number” ; cin >> n ; if ( n < 0 ) ; throw runtime_error( “negative n” ) ; // .. etc. } anonymous construction! NOT new runtime_error( ... ) ; We are not throwing a pointer! NKU CSC 601 Fall 2002 K. Kirby

  8. Catching a standard exception... by reference? void something() { try { // ... etc. f() ; // ... etc . } catch ( runtime_error& e ) { cerr << “Caught:” << e.what() << endl ; } } what is a reference, really? NKU CSC 601 Fall 2002 K. Kirby

  9. Specifications Say what you are going to throw. This includes what is thrown (and uncaught) by functions you call yourself. List everything that could be thrown: void f() throw ( runtime_error, logic_error ) ; To say f won’t throw anything, write this: void f() throw() ; This means “might throw anything”: void something() ; Not “throws” (contra Java) NKU CSC 601 Fall 2002 K. Kirby

  10. The Best Thing About Exception Handling When an exception is thrown out of a function, all destructors of objects named by local variables are called. NKU CSC 601 Fall 2002 K. Kirby

  11. When an exception is thrown out of a function, all destructors of objects named by local variables are called. To benefit from this nice feature... Do this: DON’T DO THIS! void f( int n ) { Thing th( 7 ) ; vector<int> v( n ) ; // stuff... } void f( int n ) { Thing* pt= new Thing(7) ; int* ar= new int[n] ; // stuff... delete pt ; delete [] ar ; } Avoid dumb pointers if you can! NKU CSC 601 Fall 2002 K. Kirby

  12. void recur( int n ) throw ( invalid_argument ) { SomeClass c ; if ( n < 0 ) throw ( invalid_argument( "Negative argument" ) ); else if ( n == 0 ) cout << "...bottom!" << endl ; else recur( n-2 ) ; } void play( int n ) throw ( logic_error ) { recur( n ) ; } void starter() throw () { try { play( 4 ) ; // should be okay play( 3 ) ; // asking for trouble } catch ( logic_error& e ) { cout << "CAUGHT: " << e.what() << endl ; } } main() { starter() ; } Exceptions: A Tour NKU CSC 601 Fall 2002 K. Kirby

  13. void recur( int n ) throw ( invalid_argument ) { SomeClass c ; if ( n < 0 ) throw ( invalid_argument( "Negative argument" ) ); else if ( n == 0 ) cout << "...bottom!" << endl ; else recur( n-2 ) ; } void play( int n ) throw ( logic_error ) { recur( n ) ; } void starter() throw () { try { play( 4 ) ; // should be okay play( 3 ) ; // asking for trouble } catch ( logic_error& e ) { cout << "CAUGHT: " << e.what() << endl ; } } main() { starter() ; } main The Heap The Stack NKU CSC 601 Fall 2002 K. Kirby

  14. void recur( int n ) throw ( invalid_argument ) { SomeClass c ; if ( n < 0 ) throw ( invalid_argument( "Negative argument" ) ); else if ( n == 0 ) cout << "...bottom!" << endl ; else recur( n-2 ) ; } void play( int n ) throw ( logic_error ) { recur( n ) ; } void starter() throw () { try { play( 4 ) ; // should be okay play( 3 ) ; // asking for trouble } catch ( logic_error& e ) { cout << "CAUGHT: " << e.what() << endl ; } } main() { starter() ; } starter main The Heap The Stack NKU CSC 601 Fall 2002 K. Kirby

  15. void recur( int n ) throw ( invalid_argument ) { SomeClass c ; if ( n < 0 ) throw ( invalid_argument( "Negative argument" ) ); else if ( n == 0 ) cout << "...bottom!" << endl ; else recur( n-2 ) ; } void play( int n ) throw ( logic_error ) { recur( n ) ; } void starter() throw () { try { play( 4 ) ; // should be okay play( 3 ) ; // asking for trouble } catch ( logic_error& e ) { cout << "CAUGHT: " << e.what() << endl ; } } main() { starter() ; } starter main The Heap The Stack NKU CSC 601 Fall 2002 K. Kirby

  16. void recur( int n ) throw ( invalid_argument ) { SomeClass c ; if ( n < 0 ) throw ( invalid_argument( "Negative argument" ) ); else if ( n == 0 ) cout << "...bottom!" << endl ; else recur( n-2 ) ; } void play( int n ) throw ( logic_error ) { recur( n ) ; } void starter() throw () { try { play( 4 ) ; // should be okay play( 3 ) ; // asking for trouble } catch ( logic_error& e ) { cout << "CAUGHT: " << e.what() << endl ; } } main() { starter() ; } play(4) starter main The Heap The Stack NKU CSC 601 Fall 2002 K. Kirby

  17. void recur( int n ) throw ( invalid_argument ) { SomeClass c ; if ( n < 0 ) throw ( invalid_argument( "Negative argument" ) ); else if ( n == 0 ) cout << "...bottom!" << endl ; else recur( n-2 ) ; } void play( int n ) throw ( logic_error ) { recur( n ) ; } void starter() throw () { try { play( 4 ) ; // should be okay play( 3 ) ; // asking for trouble } catch ( logic_error& e ) { cout << "CAUGHT: " << e.what() << endl ; } } main() { starter() ; } recur(4) c play(4) starter main The Heap The Stack NKU CSC 601 Fall 2002 K. Kirby

  18. void recur( int n ) throw ( invalid_argument ) { SomeClass c ; if ( n < 0 ) throw ( invalid_argument( "Negative argument" ) ); else if ( n == 0 ) cout << "...bottom!" << endl ; else recur( n-2 ) ; } void play( int n ) throw ( logic_error ) { recur( n ) ; } void starter() throw () { try { play( 4 ) ; // should be okay play( 3 ) ; // asking for trouble } catch ( logic_error& e ) { cout << "CAUGHT: " << e.what() << endl ; } } main() { starter() ; } recur(4) c play(4) starter main The Heap The Stack NKU CSC 601 Fall 2002 K. Kirby

  19. void recur( int n ) throw ( invalid_argument ) { SomeClass c ; if ( n < 0 ) throw ( invalid_argument( "Negative argument" ) ); else if ( n == 0 ) cout << "...bottom!" << endl ; else recur( n-2 ) ; } void play( int n ) throw ( logic_error ) { recur( n ) ; } void starter() throw () { try { play( 4 ) ; // should be okay play( 3 ) ; // asking for trouble } catch ( logic_error& e ) { cout << "CAUGHT: " << e.what() << endl ; } } main() { starter() ; } recur(4) c play(4) starter main The Heap The Stack NKU CSC 601 Fall 2002 K. Kirby

  20. void recur( int n ) throw ( invalid_argument ) { SomeClass c ; if ( n < 0 ) throw ( invalid_argument( "Negative argument" ) ); else if ( n == 0 ) cout << "...bottom!" << endl ; else recur( n-2 ) ; } void play( int n ) throw ( logic_error ) { recur( n ) ; } void starter() throw () { try { play( 4 ) ; // should be okay play( 3 ) ; // asking for trouble } catch ( logic_error& e ) { cout << "CAUGHT: " << e.what() << endl ; } } main() { starter() ; } recur(2) c recur(4) c play(4) starter main The Heap The Stack NKU CSC 601 Fall 2002 K. Kirby

  21. void recur( int n ) throw ( invalid_argument ) { SomeClass c ; if ( n < 0 ) throw ( invalid_argument( "Negative argument" ) ); else if ( n == 0 ) cout << "...bottom!" << endl ; else recur( n-2 ) ; } void play( int n ) throw ( logic_error ) { recur( n ) ; } void starter() throw () { try { play( 4 ) ; // should be okay play( 3 ) ; // asking for trouble } catch ( logic_error& e ) { cout << "CAUGHT: " << e.what() << endl ; } } main() { starter() ; } recur(2) c recur(4) c play(4) starter main The Heap The Stack NKU CSC 601 Fall 2002 K. Kirby

  22. void recur( int n ) throw ( invalid_argument ) { SomeClass c ; if ( n < 0 ) throw ( invalid_argument( "Negative argument" ) ); else if ( n == 0 ) cout << "...bottom!" << endl ; else recur( n-2 ) ; } void play( int n ) throw ( logic_error ) { recur( n ) ; } void starter() throw () { try { play( 4 ) ; // should be okay play( 3 ) ; // asking for trouble } catch ( logic_error& e ) { cout << "CAUGHT: " << e.what() << endl ; } } main() { starter() ; } recur(2) c recur(4) c play(4) starter main The Heap The Stack NKU CSC 601 Fall 2002 K. Kirby

  23. void recur( int n ) throw ( invalid_argument ) { SomeClass c ; if ( n < 0 ) throw ( invalid_argument( "Negative argument" ) ); else if ( n == 0 ) cout << "...bottom!" << endl ; else recur( n-2 ) ; } void play( int n ) throw ( logic_error ) { recur( n ) ; } void starter() throw () { try { play( 4 ) ; // should be okay play( 3 ) ; // asking for trouble } catch ( logic_error& e ) { cout << "CAUGHT: " << e.what() << endl ; } } main() { starter() ; } recur(0) c recur(2) c recur(4) c play(4) starter main The Heap The Stack NKU CSC 601 Fall 2002 K. Kirby

  24. void recur( int n ) throw ( invalid_argument ) { SomeClass c ; if ( n < 0 ) throw ( invalid_argument( "Negative argument" ) ); else if ( n == 0 ) cout << "...bottom!" << endl ; else recur( n-2 ) ; } void play( int n ) throw ( logic_error ) { recur( n ) ; } void starter() throw () { try { play( 4 ) ; // should be okay play( 3 ) ; // asking for trouble } catch ( logic_error& e ) { cout << "CAUGHT: " << e.what() << endl ; } } main() { starter() ; } recur(0) c recur(2) c recur(4) c play(4) starter main The Heap The Stack NKU CSC 601 Fall 2002 K. Kirby

  25. void recur( int n ) throw ( invalid_argument ) { SomeClass c ; if ( n < 0 ) throw ( invalid_argument( "Negative argument" ) ); else if ( n == 0 ) cout << "...bottom!" << endl ; else recur( n-2 ) ; } void play( int n ) throw ( logic_error ) { recur( n ) ; } void starter() throw () { try { play( 4 ) ; // should be okay play( 3 ) ; // asking for trouble } catch ( logic_error& e ) { cout << "CAUGHT: " << e.what() << endl ; } } main() { starter() ; } …bottom! recur(0) c recur(2) c recur(4) c play(4) starter main The Heap The Stack NKU CSC 601 Fall 2002 K. Kirby

  26. void recur( int n ) throw ( invalid_argument ) { SomeClass c ; if ( n < 0 ) throw ( invalid_argument( "Negative argument" ) ); else if ( n == 0 ) cout << "...bottom!" << endl ; else recur( n-2 ) ; } void play( int n ) throw ( logic_error ) { recur( n ) ; } void starter() throw () { try { play( 4 ) ; // should be okay play( 3 ) ; // asking for trouble } catch ( logic_error& e ) { cout << "CAUGHT: " << e.what() << endl ; } } main() { starter() ; } …bottom! recur(2) dtor called c recur(4) c play(4) starter main The Heap The Stack NKU CSC 601 Fall 2002 K. Kirby

  27. void recur( int n ) throw ( invalid_argument ) { SomeClass c ; if ( n < 0 ) throw ( invalid_argument( "Negative argument" ) ); else if ( n == 0 ) cout << "...bottom!" << endl ; else recur( n-2 ) ; } void play( int n ) throw ( logic_error ) { recur( n ) ; } void starter() throw () { try { play( 4 ) ; // should be okay play( 3 ) ; // asking for trouble } catch ( logic_error& e ) { cout << "CAUGHT: " << e.what() << endl ; } } main() { starter() ; } …bottom! recur(4) c dtor called play(4) starter main The Heap The Stack NKU CSC 601 Fall 2002 K. Kirby

  28. void recur( int n ) throw ( invalid_argument ) { SomeClass c ; if ( n < 0 ) throw ( invalid_argument( "Negative argument" ) ); else if ( n == 0 ) cout << "...bottom!" << endl ; else recur( n-2 ) ; } void play( int n ) throw ( logic_error ) { recur( n ) ; } void starter() throw () { try { play( 4 ) ; // should be okay play( 3 ) ; // asking for trouble } catch ( logic_error& e ) { cout << "CAUGHT: " << e.what() << endl ; } } main() { starter() ; } …bottom! play(4) starter dtor called main The Heap The Stack NKU CSC 601 Fall 2002 K. Kirby

  29. void recur( int n ) throw ( invalid_argument ) { SomeClass c ; if ( n < 0 ) throw ( invalid_argument( "Negative argument" ) ); else if ( n == 0 ) cout << "...bottom!" << endl ; else recur( n-2 ) ; } void play( int n ) throw ( logic_error ) { recur( n ) ; } void starter() throw () { try { play( 4 ) ; // should be okay play( 3 ) ; // asking for trouble } catch ( logic_error& e ) { cout << "CAUGHT: " << e.what() << endl ; } } main() { starter() ; } …bottom! starter main The Heap The Stack NKU CSC 601 Fall 2002 K. Kirby

  30. void recur( int n ) throw ( invalid_argument ) { SomeClass c ; if ( n < 0 ) throw ( invalid_argument( "Negative argument" ) ); else if ( n == 0 ) cout << "...bottom!" << endl ; else recur( n-2 ) ; } void play( int n ) throw ( logic_error ) { recur( n ) ; } void starter() throw () { try { play( 4 ) ; // should be okay play( 3 ) ; // asking for trouble } catch ( logic_error& e ) { cout << "CAUGHT: " << e.what() << endl ; } } main() { starter() ; } …bottom! play(3) starter main The Heap The Stack NKU CSC 601 Fall 2002 K. Kirby

  31. void recur( int n ) throw ( invalid_argument ) { SomeClass c ; if ( n < 0 ) throw ( invalid_argument( "Negative argument" ) ); else if ( n == 0 ) cout << "...bottom!" << endl ; else recur( n-2 ) ; } void play( int n ) throw ( logic_error ) { recur( n ) ; } void starter() throw () { try { play( 4 ) ; // should be okay play( 3 ) ; // asking for trouble } catch ( logic_error& e ) { cout << "CAUGHT: " << e.what() << endl ; } } main() { starter() ; } …bottom! recur(3) c play(3) starter main The Heap The Stack NKU CSC 601 Fall 2002 K. Kirby

  32. void recur( int n ) throw ( invalid_argument ) { SomeClass c ; if ( n < 0 ) throw ( invalid_argument( "Negative argument" ) ); else if ( n == 0 ) cout << "...bottom!" << endl ; else recur( n-2 ) ; } void play( int n ) throw ( logic_error ) { recur( n ) ; } void starter() throw () { try { play( 4 ) ; // should be okay play( 3 ) ; // asking for trouble } catch ( logic_error& e ) { cout << "CAUGHT: " << e.what() << endl ; } } main() { starter() ; } …bottom! recur(1) c recur(3) c play(3) starter main The Heap The Stack NKU CSC 601 Fall 2002 K. Kirby

  33. void recur( int n ) throw ( invalid_argument ) { SomeClass c ; if ( n < 0 ) throw ( invalid_argument( "Negative argument" ) ); else if ( n == 0 ) cout << "...bottom!" << endl ; else recur( n-2 ) ; } void play( int n ) throw ( logic_error ) { recur( n ) ; } void starter() throw () { try { play( 4 ) ; // should be okay play( 3 ) ; // asking for trouble } catch ( logic_error& e ) { cout << "CAUGHT: " << e.what() << endl ; } } main() { starter() ; } …bottom! recur(-1) c recur(1) c recur(3) c play(3) starter main The Heap The Stack NKU CSC 601 Fall 2002 K. Kirby

  34. void recur( int n ) throw ( invalid_argument ) { SomeClass c ; if ( n < 0 ) throw ( invalid_argument( "Negative argument" ) ); else if ( n == 0 ) cout << "...bottom!" << endl ; else recur( n-2 ) ; } void play( int n ) throw ( logic_error ) { recur( n ) ; } void starter() throw () { try { play( 4 ) ; // should be okay play( 3 ) ; // asking for trouble } catch ( logic_error& e ) { cout << "CAUGHT: " << e.what() << endl ; } } main() { starter() ; } …bottom! recur(-1) c recur(1) c recur(3) c play(3) starter main The Heap The Stack NKU CSC 601 Fall 2002 K. Kirby

  35. void recur( int n ) throw ( invalid_argument ) { SomeClass c ; if ( n < 0 ) throw ( invalid_argument( "Negative argument" ) ); else if ( n == 0 ) cout << "...bottom!" << endl ; else recur( n-2 ) ; } void play( int n ) throw ( logic_error ) { recur( n ) ; } void starter() throw () { try { play( 4 ) ; // should be okay play( 3 ) ; // asking for trouble } catch ( logic_error& e ) { cout << "CAUGHT: " << e.what() << endl ; } } main() { starter() ; } …bottom! recur(1) dtor called c recur(3) c play(3) starter main The Heap The Stack NKU CSC 601 Fall 2002 K. Kirby

  36. void recur( int n ) throw ( invalid_argument ) { SomeClass c ; if ( n < 0 ) throw ( invalid_argument( "Negative argument" ) ); else if ( n == 0 ) cout << "...bottom!" << endl ; else recur( n-2 ) ; } void play( int n ) throw ( logic_error ) { recur( n ) ; } void starter() throw () { try { play( 4 ) ; // should be okay play( 3 ) ; // asking for trouble } catch ( logic_error& e ) { cout << "CAUGHT: " << e.what() << endl ; } } main() { starter() ; } …bottom! recur(3) c dtor called play(3) starter main The Heap The Stack NKU CSC 601 Fall 2002 K. Kirby

  37. void recur( int n ) throw ( invalid_argument ) { SomeClass c ; if ( n < 0 ) throw ( invalid_argument( "Negative argument" ) ); else if ( n == 0 ) cout << "...bottom!" << endl ; else recur( n-2 ) ; } void play( int n ) throw ( logic_error ) { recur( n ) ; } void starter() throw () { try { play( 4 ) ; // should be okay play( 3 ) ; // asking for trouble } catch ( logic_error& e ) { cout << "CAUGHT: " << e.what() << endl ; } } main() { starter() ; } …bottom! play(3) starter dtor called main The Heap The Stack NKU CSC 601 Fall 2002 K. Kirby

  38. void recur( int n ) throw ( invalid_argument ) { SomeClass c ; if ( n < 0 ) throw ( invalid_argument( "Negative argument" ) ); else if ( n == 0 ) cout << "...bottom!" << endl ; else recur( n-2 ) ; } void play( int n ) throw ( logic_error ) { recur( n ) ; } void starter() throw () { try { play( 4 ) ; // should be okay play( 3 ) ; // asking for trouble } catch ( logic_error& e ) { cout << "CAUGHT: " << e.what() << endl ; } } main() { starter() ; } …bottom! CAUGHT: Negative argument starter main The Heap The Stack NKU CSC 601 Fall 2002 K. Kirby

  39. void recur( int n ) throw ( invalid_argument ) { SomeClass c ; if ( n < 0 ) throw ( invalid_argument( "Negative argument" ) ); else if ( n == 0 ) cout << "...bottom!" << endl ; else recur( n-2 ) ; } void play( int n ) throw ( logic_error ) { recur( n ) ; } void starter() throw () { try { play( 4 ) ; // should be okay play( 3 ) ; // asking for trouble } catch ( logic_error& e ) { cout << "CAUGHT: " << e.what() << endl ; } } main() { starter() ; } …bottom! CAUGHT: Negative argument main The Heap The Stack NKU CSC 601 Fall 2002 K. Kirby

  40. void recur( int n ) throw ( invalid_argument ) { SomeClass c ; if ( n < 0 ) throw ( invalid_argument( "Negative argument" ) ); else if ( n == 0 ) cout << "...bottom!" << endl ; else recur( n-2 ) ; } void play( int n ) throw ( logic_error ) { recur( n ) ; } void starter() throw () { try { play( 4 ) ; // should be okay play( 3 ) ; // asking for trouble } catch ( logic_error& e ) { cout << "CAUGHT: " << e.what() << endl ; } } main() { starter() ; } The Heap The Stack NKU CSC 601 Fall 2002 K. Kirby

  41. Memory Overflow For the New Millennium 20th century: int* p = new int [ BIGNUM ] ; if ( p == NULL ) // sorry, could not allocate else // use p[] 21st century: will throw a bad_alloc exception if allocation fails (catch it if you like) #include <memory> int* p = new int [ BIGNUM ] ; // use p[] NKU CSC 601 Fall 2002 K. Kirby

More Related