C + + exception handling

Source: Internet
Author: User
Tags throw exception

Introduction

In the process of programming, we always want to design the program is seamless, but this is almost impossible. Even if the program is compiled and implemented with the required functionality, it does not mean that the program is perfect, because it is possible to run the program with exceptions, such as when we design a program that calculates division for the user, the user is likely to enter the divisor as zero. Another example is when we need to open a file to find that the file has been deleted ... There are many similar situations where it is not possible to prevent them from being protected against these special circumstances.

We usually hope that the program we write can be handled in an unusual way, without the program interrupting or aborting the operation somehow. When designing a program, you should take full account of the various anomalies and deal with them.

In C + +, a function can detect an exception and return an exception, a mechanism known as throwing an exception. When an exception is thrown, the function caller catches the exception and processes the exception, which we call an exception capture.

The new C + + keyword throw is used to throw exceptions, new keywords are catch used to catch exceptions, and new try keywords try to catch exceptions. You typically place the statement that you are trying to capture in a try{ } block, and the exception-handling statement catch{ } in a statement block.

Exception handling mechanism

The exception handling mechanism provided by C + + allows programmers to capture exceptions themselves and handle them on their own, depending on the type of exception caught, which gives programmers greater control over their own programs.
Exception handling requires the following three keywords: try, throw, catch.

Basic exception Handler Framework

try{    //可能出现异常的代码块}catch(类型名1 [形参名])   //这里形参名可以不出现{    //捕获到 类型名1 的异常时的异常处理程序}catch(类型名1 [形参名]){    //捕获到 类型名2 的异常时的异常处理程序}...catch(...){    //三个点 表示可以捕获任何异常}

First, an exception is thrown using throw, which is syntax:

throw 表达式

When used, a statement block that may throw an exception is included in the try{} statement block, and if the try{} program in the block of statements finds an exception and throws the exception, then the exception can be captured and processed by the statement, and the catch{} condition that is caught and processed is the type catch of the thrown exception and Match the exception type of the statement. Because C + + uses data types to differentiate between different exceptions, when judging an exception, the value of the throw expression in the statement has no practical significance, and the type of the expression is particularly important.

Throw a built-in type

C + + can throw exceptions of ordinary built-in types
  

#include <iostream.h> //Include header files #include <stdlib.h>DoubleFucDoubleXDoubleY//define Functions{if(y==0)      {ThrowY//divisor is 0, throws an exception}returnX/y;//Return two number of quotient}voidMain () {DoubleResTry  //define Exceptions{RES=FUC (2,3);cout<<"The result of X/y is:"<<res<<endl; RES=FUC (4,0); An exception occurs and an exception is thrown inside the function}Catch(Double)//catch and handle exceptions{Cerr<<"error of dividing zero.\n";Exit(1);//Abnormal Exit program}  }

The above program throws a type of exception when the divisor is 0, double and then handles the following catch{} catch exception.

Throw a custom exception type

  
The exception type can make a custom exception class, and the exception class is thrown in the program.
  

#include <stdlib.h>#include <crtdbg.h>#include <iostream>//memory leak detection mechanism#define _CRTDBG_MAP_ALLOC#ifdef _DEBUG#define NEW New (_normal_block, __file__, __line__)#endif//Custom Exception classclassmyexcepction { Public://constructor, parameter is error codeMyexcepction (intErrorID) {//Output constructor is called information            STD::cout<<"Myexcepction is called"<<STD:: Endl;          M_errorid = ErrorID; }//Copy constructorMyexcepction (myexcepction& myexp) {//Output copy constructor called Information            STD::cout<<"Copy construct is called"<<STD:: Endl; This->m_errorid = Myexp.m_errorid; } ~myexcepction () {//Output destructor is called information            STD::cout<<"~myexcepction is called"<<STD:: Endl; }//Get error codes        intGeterrorid () {returnM_errorid; }Private://Error code        intM_errorid; };intMainintargcChar* argv[]) {//memory leak detection mechanism_CrtSetDbgFlag (_CRTDBG_ALLOC_MEM_DF | _crtdbg_leak_check_df);//Can change the error code in order to throw different exceptions for testing        intThrowerrorcode = the;STD::cout<<"Input test code:"<<STD:: Endl;STD::Cin>> Throwerrorcode;Try{if(Throwerrorcode = = the) {Myexcepction Mystru ( the);//The address of the thrown object is captured by catch (myexcepction* pmyexcepction)                //Here the address of the object is thrown to the catch statement and the copy constructor of the object is not called                //Pass address is a advocated practice and does not frequently call the object's constructor or copy constructor                Mystru will be destroyed when the//Catch statement finishes executing                Throw&myStru; }Else if(Throwerrorcode = =119) {Myexcepction Mystru (119);//throws the object, where a temporary object is created by copying the constructor out to the catch                //Captured by catch (Myexcepction myexcepction)                //In the catch statement is called again by the copy constructor to create the temporary object copy the object passed here                //Mystru will be destroyed after the throw is over                ThrowMystru; }Else if(Throwerrorcode = = -)               {//Do not advocate such a throw method                  //To do so, a memory leak occurs if the delete operation is not performed in catch (myexcepction* pmyexcepction)                  //Captured by catch (myexcepction* pmyexcepction)Myexcepction * Pmystru =NewMyexcepction ( -);ThrowPmystru; }Else{//Create new object directly throw                  //equivalent to the creation of a temporary object passed to the Catch statement                  //received by catch when the temporary object is created again by the copy constructor receive passing past objects                  //The temporary objects created two times after the throw end are destroyed                   ThrowMyexcepction (Throwerrorcode); }              }Catch(myexcepction* pmyexcepction) {//Output This statement is executed information               STD::cout<<"A catch was executed (myexcepction* pmyexcepction)"<<STD:: Endl;//Output error message               STD::cout<<"error Code:"<< Pmyexcepction->geterrorid () <<STD:: Endl;//The new object thrown by the exception is not created on the function stack, but is created on a dedicated exception stack and does not require a delete            //delete pmyexcepction; }Catch(Myexcepction myexcepction) {//Output This statement is executed information            STD::cout<<"A catch was executed (myexcepction myexcepction)"<<STD:: Endl;//Output error message            STD::cout<<"error Code:"<< Myexcepction.geterrorid () <<STD:: Endl; }Catch(...) {//Output This statement is executed information             STD::cout<<"a catch (...) was executed."<<STD:: Endl;//cannot be processed, re-thrown to superiors             Throw; }//Pause        intTempSTD::Cin>> temp;return 0; }

The following example can also be a good illustration of

 class numberparseexception {};//Determine if the string is a numberBOOL Isnumber (Char*Str) {using namespace std;if(Str= = NULL)return false;intLen = strlen (Str);if(len = =0)return false; BOOL Isanumber =false;CharCh for(inti =0; i < Len; i++) {if(i = =0&& (Str[I] = ='-'||Str[I] = =' + '))Continue;if(IsDigit (Str[i])) {Isanumber =true; }Else{Isanumber =false; Break; }     }returnIsanumber;}//Not a number throws an exceptionintParsenumber (Char*Str)Throw(numberparseexception) {if(!isnumber (Str))ThrowNumberparseexception ();returnAtoiStr);}
The interface type of the exception

In order to enhance the readability of the program, the user of the function is able to easily know what exceptions the function will throw, and when the interface declares it, it needs to label the throw exception.

List all exceptions that may be thrown
voidthrow(A, B, C, D);

This indicates that the function fun () May and may only throw exceptions of type (A, B, C, D) and its subtypes .

Throws any type of exception
voidfun();

This indicates that the function can throw any type of exception

Does not throw any type exceptions
voidfun() thow();

This indicates that the function does not throw any type of exception

Catching exceptions

The code that catches the exception is generally as follows:

try {    throw E();     //在try中抛出了类型为E的异常}catch (H h) {     //何时我们可以能到这里呢}

1. If H and e are the same type

2. If h is the base class for E

3. If both H and e are pointer types, and 1 or 2 are valid for the type they reference

4. If both H and e are reference types, and 1 or 2 of the types referenced by H are established

In principle, exceptions are duplicated when thrown, and the last exception we catch is just a copy of the original exception, so we should not throw an exception that does not allow a copy to be thrown.

In addition, we can add a const to the type used to catch the exception, just as we can add a const to the function, restricting us from modifying the caught exception.

Also, if the exception is caught when H and e are not reference types or pointer types, and H is the base class of E, then the H object is actually h H = e (), and the last caught exception object H loses the additional carrying information of E.

To re-throw an exception

When we catch an exception and find that we cannot handle it, in this case, we will do what we can do locally, and then throw the exception again and let the exception be handled in the most appropriate place. For example:
  

void downloadFileFromServer() {    try {          connect_to_server();          //...     }       catch (NetworkException) {           if (can_handle_it_completely) {               //处理网络异常,例如重连           else {                throw;            }       }}

This function is to download the file from the remote server, internal calls to connect to the remote server function, but there may be a network exception, if multiple reconnection cannot succeed, throw this network exception, let the upper processing.

A re-throw is a representation without an operand, throw but if it is re-thrown and no exception can be re-thrown, it will be called terminate() ;

Suppose that NetworkException there are two derived exceptions called FtpConnectException and HttpConnectException that connect_to_server are thrown when called HttpConnectException , then downloadFileFromServer the call can still catch the exception HttpConnectException .

Standard exceptions

Here, you have basically used the exception, but if you are a function developer, and need to use the function to others, when using exceptions, will involve the custom exception class, but the C + + standard has defined a part of the standard exception, please reuse these exceptions as possible, the standard exception reference HTTP./ www.cplusplus.com/reference/std/stdexcept/

Although the C + + standard exception is relatively small, but as a function developer, as much as possible to reuse the C + + standard exception, as a function caller can spend less time to understand your custom exception class, better to call the function you developed.

C + + exception handling

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.