通常,引发异常的函数将传递一个对象。这样做的重要有点之一是,可以使用不同的异常类型来区分不同的函数在不同情况下引发的异常。另外,对象可以携带信息,程序员可以根据这些信息来确定引发异常的原因。同时,catch块可以根据这些信息来决定采取什么样的措施。
下面的两个程序用语言是这个效果。如果函数hmean()引发bad_mean异常,第一个catch块将捕获该异常;如果gmean()引发bad_gmaen异常,异常将逃过第一个catch块,被第二个catch块捕获。
exc_mean.h

// exc_mean.h -- exception classes for hmean(), gmean()
#include <iostream> class bad_hmean
{
private:
double v1;
double v2;
public:
bad_hmean(double a = , double b = ) : v1(a), v2(b) {}
void mesg();
}; inline void bad_hmean::mesg()
{
std::cout << "hmean(" << v1 << ", " << v2 << "): "
<< "invalid arguments: a = -b\n";
}
class bad_gmean
{
public:
double v1;
double v2;
bad_gmean(double a = , double b = ) : v1(a), v2(b) {}
const char * mesg();
}; inline const char * bad_gmean::mesg()
{
return "gmean() arguments should be >= 0\n";
}

error4.cpp

// error4.cpp -- using exception classes
#include <iostream>
#include <cmath> // or math.h, unix users may need -lm flag
#include "exc_mean.h"
// function prototypes
double hmean(double a, double b);
double gmean(double a, double b); int main()
{
using std::cin;
using std::cout;
using std::endl; double x, y, z; cout << "Enter two numbers: ";
while (cin >> x >> y)
{
try { // start of try block
z = hmean(x, y);
cout << "Harmonic mean of " << x << " and " << y
<< " is " << z << endl;
cout << "Geometric mean of " << x << " and " << y
<< " is " << gmean(x, y) << endl;
cout << "Enter next set of numbers <q to quit>: ";
} // end of try block
catch (bad_hmean & bg) // start of catch block
{
bg.mesg();
cout << "Try again.\n";
continue;
}
catch (bad_gmean & hg)
{
cout << hg.mesg();
cout << "Values used: " << hg.v1 << ", "
<< hg.v2 << endl;
cout << "Sorry, you don't get to play any more.\n";
break;
} // end of catch block
}
cout << "Bye!\n";
return ;
} double hmean(double a, double b)
{
if (a == -b)
throw bad_hmean(a, b);
return 2.0 * a * b / (a + b);
} double gmean(double a, double b)
{
if (a < | b < )
throw bad_gmean(a, b);
return std::sqrt(a * b);
}

效果:

Enter two numbers: 4 12
Harmonic mean of 4 and 12 is 6
Geometric mean of 4 and 12 is 6.9282
Enter next set of numbers <q to quit>: 5 -5
hmean(5, -5): invalid arguments: a = -b
Try again.
5 -2
Harmonic mean of 5 and -2 is -6.66667
gmean() arguments should be >= 0
Values used: 5, -2
Sorry, you don't get to play any more.
Bye!

C++异常 将对象用作异常类型的更多相关文章

  1. C++_异常4-将对象用作异常类型

    通常,引发异常的函数将传递一个对象.这样做的重要优点之一就是,可以利用不同的异常类型来区分不同的函数在不同的情况下引发的异常. 对象可以携带信息,程序员可以根据这些信息来确定异常的原因. 同时,cat ...

  2. C++异常处理 - 栈解旋,异常接口声明,异常类型和异常变量的生命周期

    栈解旋(unwinding) 异常被抛出后,从进入try块起,到异常被抛掷前,这期间在栈上的构造的所有对象,都会被自动析构.析构的顺序与构造的顺序相反.这一过程称为栈的解旋(unwinding). d ...

  3. 【C/C++学院】0831-类与对象的异常/面试100题1-100

    类与对象的异常 Cpp异常 #include <iostream> #include <string.h> using namespace std; //标识错误的类型 cla ...

  4. CLR如何将SEH异常映射到托管异常类型

    托管异常处理构建在Windows操作系统的结构化异常处理之上,通常称为SEH.这意味着CLR了解如何在SEH和托管异常系统之间进行互操作,这是一个非常关键的点,因为SEH基于异常代码的概念,而托管异常 ...

  5. 将对象的所有属性名放到一个数组中 || 获得对象的所有属性名 || return;不具有原子性 || 怎样自己制作异常|| 判断对象有没有某个属性 || 当传递的参数比需要的参数少的时候,没有的值会被赋予undefined || 获得函数实际传递的参数 || 怎么用函数处理一个对象 || 用一个名字空间定义一个模块所有的函数 || 给一个对象添加方法

    获得对象的所有属性名 || 将对象o的所有属性名放到数组中 var o = {x:1,y:2,z:3}; var arr = []; var i = 0; for(arr[i++] in o){};/ ...

  6. 【转】【C#】异常类 Exception 枚举所有类型的异常

    一.基础 在C# 里,异常处理就是C# 为处理错误情况提供的一种机制.它为每种错误情况提供了定制的处理方式,并且把标识错误的代码与处理错误的代码分离开来. 对.NET类来说,一般的 异常类System ...

  7. Net使用RdKafka引发异常RdKafka.Internal.LibRdKafka 的类型初始值设定项引发异常

    在Net中VS2015用RdKafka组件开发消息发布和消费,引发下面的异常 RdKafka.Internal.LibRdKafka 的类型初始值设定项引发异常System.TypeInitializ ...

  8. 34 异常机制 异常体系结构 Java把异常当做对象来处理 并定义一个基类java.lang.Throwable作为所有异常的超类 Error Exception

    异常体系结构 概念 Java把异常当做对象来处理,并定义一个基类java.lang.Throwable作为所有异常的超类. 在Java API中已经定义了许多异常类,这些异常类分为两大类,错误Erro ...

  9. c# 变量,对象,静态类型,集合类的线程安全回顾

    1.变量的线程安全性与变量的作用域有关. 2.对象 对象是类型的实例 在创建对象时,会单独有内存区域存储对象的属性和方法.所以,一个类型的多个实例,在执行时,只要没有静态变量的参与,应该都是线程安全的 ...

随机推荐

  1. activemq5.11整合spring4.2.3

    前言 这篇博客记录 activemq5.11整合spring4.2.3的过程,免得以后忘记了 1.工程结构 2.pom.xml <project xmlns="http://maven ...

  2. CentOS 修改系统语言的方法

    使用如下命令: export LANG="en_US.UTF-8" 可以修改环境变量LANG,修改之后立即生效,当时当系统重新启动时便会又变成原来的语言 另外两种修改语言的方法: ...

  3. buildroot 使用本地交叉编译器记录

    继上一次glibc bug 事件后,剑锋就说文件系统要用统一的交叉编译器.所以今天就试了一下,便记录一下 在官网下载干净的 buildroot 进入解压后的 buildroot 目录 步骤: make ...

  4. FusionCharts JavaScript API - Events 全局事件处理

    FusionCharts JavaScript API - Events 全局事件处理 Home > FusionCharts XT and JavaScript > API Refere ...

  5. 页面装载js及性能分析方法

    一.装载 先装载静态页面的引用js文件,然后查找引用文件中是否包含onload函数,比如main.js中包含onload函数,在main.js中查找是否有对其他js文件的引用,优先装载引用js文件,被 ...

  6. Windoows窗口程序四

    子窗口的创建 .创建时要设置父窗口句柄 .创建风格要增加WS_CHILD|WS_VISIBLE HWND CreateChild(LPSTR lpClassName,LPSTR lpWndName,H ...

  7. php 添加数据库的几种方法

    最简单的 <?php $con = mysql_connect("localhost","root","root"); if (!$c ...

  8. appium的inspectot使用

    前提已安装好appium环境 1. 打开appium-doctor 2. 启动appium-service,点击  inspector 3. 配置手机参数,参数获取参考上篇博客 4. 点击start ...

  9. linux -- Ubuntu下安装和配置Apache2

    在Ubuntu中安装apache 安装指令:sudo apt-get install apache2 启动和停止apache的文件是:/etc/init.d/apache2 启动命令:sudo apa ...

  10. 使用libcurl源代码编译只是的问题

    curl 7.21.6 + vs2005 就把curl的.c文件加到project中编译.报错信息非常古怪: setup_once.h(274) : error C2628: '<unnamed ...