线程安全,类型安全以及异常安全之前的共同点是它们都是为创建更为健壮的程序而被提出的。
线程安全
线程安全是指如果一个函数在同一时刻可以被多个线程安全地调用,则称该函数是线程安全的。
不具备线程安全的函数在没有保护的情况下,不能在多线程环境中正确使用。
通常,很多函数不具备线程安全性是因为它们返回的数据是存放在静态的内存缓冲区中。通过修改接口,要求
调用者自己提供缓冲区可以使函数变为线程安全
异常处理
异常,即程序运转时出现了开发者意料之外的状态,显然这些异常情况是不允许的。所以必须对异常情况有
处理。
一般在C语言中,最常见的就是诸如判断一个函数返回值得代码:
s = socket(AF_INET,SOCK_STREAM,0);
if(s < 0)
{
perror("socket call failed");
exit(1);
}
还可以使用标准C的信号处理系统,由函数signal()和raise()现实推断事件发生时出现了什么情况以及产生一
个事件。
另外较常用的就是使用setjmp() (保存一个已知的无错误状态)和longjmp()(错误发生时调用,回到那个无错误状态)
但是由于C中信号处理方法和setjmp 和longjmp并不调用析构函数,所以C++中对象不会被正确处理。
因此在标准C++中有了新的异常处理机制。
异常安全
当异常抛出时,带有异常安全的函数会:
1.不泄露任何资源
一般采用RAII技术,即以对象管(智能指针)理资源来防止资源泄漏。
2.不允许数据被破坏
异常安全函数提供以下三个保证之一:
1.基本承诺:如果抛出异常,程序内的任何事物仍然保持在有效的状态,没有任何对象或数据结构会被破坏。
2.强烈保证:如果异常抛出,程序状态不改变。调用这样的函数如果成功就完全成功,如果失败,程序回复到
“调用函数之前”的状态。
3.不抛掷保证:承诺绝不抛出异常。
对大部分函数而言,通常”基本承诺“和”强烈保证“比较实际。
copy and swap策略是一种典型的实施”强烈承诺“的手法:首先为打算修改的对象准备一份副本,然后再副本
上做一切必要修改。若有任何异常抛出则对象仍保持未改变状态。待所有改变都成功后,再将修改过的那个副
本和原对象在一个不抛出异常的操作中置换。
但有两点原因可能导致copy and swap策略失效:1.如果该函数中调用了其他异常安全性比”强烈保证“低的函数
2.处于性能方面的原因,可能无法实施copy and swap。
注意:不要为了表示某件事情的发生而改变对象状态,除非那件事情真的发生了
如果系统中有一个函数不具备异常安全性,则整个系统就不具备异常安全性
类型安全
关于类型安全维基百科解释较全面。这个话题比较大,有时间会选择一部分翻译过来。
http://en.wikipedia.org/wiki/Type_safety