建设一个网站平台的费用吗,东莞建设网站公司,品牌网,平面设计有哪些文章目录 C异常异常语法代码示例 栈解旋示例代码 noexcept代码示例 异常的声明周期示例代码 异常的多态使用代码示例 C标准异常库代码示例 重写自己的异常示例代码 C异常
异常是处理程序中的错误。所谓的错误时指程序运行的过程中发生的一些异常事件(如#xff1a;除零错误异常异常语法代码示例 栈解旋示例代码 noexcept代码示例 异常的声明周期示例代码 异常的多态使用代码示例 C标准异常库代码示例 重写自己的异常示例代码 C异常
异常是处理程序中的错误。所谓的错误时指程序运行的过程中发生的一些异常事件(如除零错误数组下标越界所要读取的文件不存在空指针内存不足等)
C异常机制相比C语言异常处理的优势
函数返回值可以忽略但是异常不可以忽略并且容易和正常结果混淆如果程序出现异常但是没有被捕获程序就会终止
异常语法
代码示例
#include iostream
#include string
#include iostream
using namespace std;
int test01()
{throw 0;return 0;
}
void test02()
{try{test01();}catch (int e){std::cout int exception e std::endl;}catch (char e){std::cout char exception e std::endl;}catch (...){std::cout normal exception std::endl;}
}
int main(int argc, char* argv[])
{test02();return 0;
}栈解旋
异常抛出后从try起到异常被抛出前这期间在栈上构造的所有对象都会被自动析构。析构的顺序与构造的顺序相反这一过程称为栈的解旋。
示例代码
#include iostream
#include string
#include iostream
using namespace std;
class Person
{
public:Person(string name1){name name1;cout Person name endl;}~Person(){cout ~Person name endl;}string name;
};
void test()
{try {Person p(1);Person p1(2);Person p2(3);throw 10;}catch (...){cout exception endl;}
}
int main(int argc, char* argv[])
{test();return 0;
}noexcept
为了加强程序可读性可以在函数声明中指定是否可以抛出异常。
例如void func() noexcept(true)表示函数函数无法抛出异常, 后面的true可省略
例如void func() noexcept(false)表示函数函数可能抛出异常
代码示例
#include iostream
#include string
#include iostream
using namespace std;
void test() noexcept(false)
{// throw 10;
}
void test01() noexcept(true)
{throw 10;
}
int main(int argc, char* argv[])
{try {test();test01();}catch (...){cout exception endl;}return 0;
}异常的声明周期
throw 的异常是有类型的可以是数字、字符串、类对象。throw的异常是有类型的catch需要严格匹配异常的类型。
示例代码
#include iostream
#include string
#include iostream
using namespace std;class MyException
{
public:MyException(){cout MyException endl;}MyException(const MyException other){cout MyException2 endl;}~MyException(){cout ~MyException endl;}
};
int test1()
{try {throw MyException();}catch (MyException e){cout exception endl;}return 0;
}
int test2()
{try {throw MyException();}catch (const MyException e){cout exception endl;}return 0;
}
int test3()
{try {throw new MyException();}catch (MyException *e){cout exception endl;delete e;e nullptr;}return 0;
}
int test4()
{try {MyException ob;throw ob;}catch (MyException e){cout exception endl;}return 0;
}
int test5()
{try {throw MyException();}catch (MyException e){cout exception endl;}return 0;
}
int main(int argc, char* argv[])
{test5();return 0;
}注意 抛出指针的时候记得析构 推荐test5()的这种方式可以提高效率。
异常的多态使用
与正常多态使用无差别
代码示例
#include iostream
#include string
#include iostream
using namespace std;
class BaseException
{
public:virtual void printLog() 0;
};
class DeriveException1 : public BaseException
{
public:void printLog() override{cout exception1 endl;}
};
void test()
{try {throw DeriveException1();}catch (BaseException e){e.printLog();}
}int main(int argc, char* argv[])
{test();return 0;
}C标准异常库
标准库中有很多的异常类它们是通过类继承组织起来的。 exception 类的直接派生类
异常名称说 明logic_error逻辑错误。runtime_error运行时错误。bad_alloc使用 new 或 new[ ] 分配内存失败时抛出的异常。bad_typeid使用 typeid 操作一个 NULL 指针而且该指针是带有虚函数的类这时抛出 bad_typeid 异常。bad_cast使用 dynamic_cast 转换失败时抛出的异常。ios_base::failureio 过程中出现的异常。bad_exception这是个特殊的异常如果函数的异常列表里声明了 bad_exception 异常当函数内部抛出了异常列表中没有的异常时如果调用的 unexpected() 函数中抛出了异常不论什么类型都会被替换为 bad_exception 类型。
logic_error 的派生类
异常名称说 明length_error试图生成一个超出该类型最大长度的对象时抛出该异常例如 vector 的 resize 操作。domain_error参数的值域错误主要用在数学函数中例如使用一个负值调用只能操作非负数的函数。out_of_range超出有效范围。invalid_argument参数不合适。在标准库中当利用string对象构造 bitset 时而 string 中的字符不是 0 或1 的时候抛出该异常。
runtime_error 的派生类
异常名称说 明range_error计算结果超出了有意义的值域范围。overflow_error算术计算上溢。underflow_error算术计算下溢。
代码示例
#include iostream
#include string
#include iostream
using namespace std;
void test(int i)
{try {if(i 50){throw out_of_range(越界);}else{throw exception(exception);}}catch (exception e){cout e.what() endl;}
}
int main(int argc, char* argv[])
{test(60);return 0;
}重写自己的异常
使用继承实现一个自己的异常(我这里是一个简单的实现)
示例代码
#include iostream
#include string
#include iostream
using namespace std;
class MyException : public exception
{
public:MyException(const char *data) noexcept: exception(data){}
};
void test(int i)
{try {throw MyException(my exception);}catch (exception e){cout e.what() endl;}
}
int main(int argc, char* argv[])
{test(60);return 0;
}