异常 堆栈解退
//函数出现异常而终止,程序将释放堆栈重内存,并一直向上释放,只到找到一个try块中的返回地址
//重新引发异常 将捕获的异常继续传回上一个try块
///////////////////////////////////////////////
//
//exc_mean.h
//
///////////////////////////////////////////////
#include<iostream>
class bad_hmean
{
private:
double v1;
double v2;
public:
bad_hmean(double a=0,double b=0):v1(a),v2(b){}
void mesg();
};
inline void bad_hmean::mesg()
{
std::cout<<"hmean("<<v1<<", "<<v2<<"):"
<<"invaild arguments:a=-b\n";
}
class bad_gmean
{
public:
double v1;
double v2;
bad_gmean(double a=0,double b=0):v1(a),v2(b){}
const char * mesg();
};
inline const char * bad_gmean::mesg()
{
return "gmean() arguments should be >=0\n";
}
///////////////////////////////////////////////////////
//
//error.cpp
//
///////////////////////////////////////////////////////
//error5.cpp -- unwinding the stack
#include <iostream>
#include <cmath> //for sqrt()
#include <cstring>
#include "exc_mean.h"
class demo
{
private:
char word[40];
public:
demo (const char * str)
{
std::strcpy(word, str);
std::cout << "demo " << word << " created\n";
}
~demo()
{
std::cout << "demo " << word << " destroyed\n";
}
void show() const
{
std::cout << "demo " << word << " lives!\n";
}
};
// function prototypes
double hmean(double a, double b) throw(bad_hmean);
double gmean(double a, double b) throw(bad_gmean);
double means(double a, double b) throw(bad_hmean, bad_gmean);
int main()
{
using std::cout;
using std::cin;
using std::endl;
double x, y, z;
demo d1("found in main()");
cout << "Enter two numbers: ";
while (cin >> x >> y)
{
try { // start of try block
z = means(x,y);
cout << "The mean mean of " << x << " and " << y
<< " is " << z << endl;
cout << "Enter next pair: ";
}// 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
}
d1.show();
cout << "Bye!\n";
return 0;
}
double hmean(double a, double b) throw(bad_hmean)
{
if (a == -b)
throw bad_hmean(a,b);
return 2.0 * a * b / (a + b);
}
double gmean(double a, double b) throw(bad_gmean)
{
if (a < 0 || b < 0)
throw bad_gmean(a,b);
return std::sqrt(a * b);
}
double means(double a, double b) throw(bad_hmean, bad_gmean)
{
double am, hm, gm;
demo d2("found in means()");
am = (a + b) / 2.0; // arithmetic mean
try
{
hm = hmean(a,b);
gm = gmean(a,b);
}
catch (bad_hmean & bg) // start of catch block
{
bg.mesg();
std::cout << "Caught in means()\n";
throw; // 重新引发异常传回main()找try
}
d2.show();
return (am + hm + gm) / 3.0;
}