目录
1. 异常处理
2. C++11 智能指针
3. 典型范例——设计和实现向量类模板
1. 异常处理
基本思想:底层检测到异常情况时抛出(throw)异常、高层可以处理异常时检查并捕捉(str...catch)异常两部分
异常的抛出和捕获:
#include#include using namespace std; double Area(double a, double b, double c) { if (a + b <= c || b + c <= a || c + a <= b) { throw "Doesn't meet the condisions of the triangle"; //异常抛出 } double p = (a + b + c) / 2; return std::sqrt(p * (p - a) * (p - b) * (p - c)); } int main() { try //可能抛出异常的序列 { cout << Area(3, 4, 5) << endl; cout << Area(3, 4, 8) << endl; cout << Area(3, 3, 3) << endl; } catch (const char* errMsg) { cout << errMsg << endl; } }
catch子句是按顺序匹配的,前面的catch子句完成匹配后,后续的catch子句不会再进行匹配
#include#include using namespace std; class A { private: char mess[18]; public: A() { strcpy(mess, "基类 A "); } const char* GetMess()const { return mess; } }; class B : public A { private: char mess[18]; public: B() { strcpy(mess, "派生类 B "); } const char* GetMess()const { return mess; } }; int main() { try { throw B(); } catch (const B& b) { cout << b.GetMess() << "类型的异常" << endl; } catch (const A& a) { cout << a.GetMess() << "类型的异常" << endl; } return 0; }
- 异常的处理:若异常未被捕获,系统调用std::terminate()函数终止程序执行
- 标准库异常分类:C++标准库提供了已定义异常类型,所有这些异常类型都派生自基类:exception
try
{
//可能抛出的异常
}
catch (exception& e)
{
//处理异常的语句
}
2. C++11 智能指针
智能指针类模板设计和实现:
#include#include using namespace std; class Song { public: Song(string strName) :m_strName(strName) {}; ~Song() { cout << "Song Destructor called" << endl; } void Play() { cout << "Play song " << m_strName << endl; } private: string m_strName; }; class Dog { public: ~Dog() { cout << "Dog Destructor called" << endl; } void Bark() { cout << "Bark! Bark!" << endl; throw 1; } }; template class smart_ptr //智能指针模板原型 { private: T* m_pRawPointer; public: smart_ptr(T* pData) :m_pRawPointer(pData) {} ~smart_ptr() { delete m_pRawPointer; } T& operator*()const //重载解引用符* { return *(m_pRawPointer); } T* operator->()const //重载运算符-> { return m_pRawPointer; } smart_ptr(smart_ptr&& anotherSP) //移动构造 { m_pRawPointer = anotherSP.m_pRawPointer; anotherSP.m_pRawPointer = nullptr; } smart_ptr& operator=(smart_ptr&& anotherSP) //移动赋值 { swap(m_pRawPointer, anotherSP.m_pRawPointer); } smart_ptr(const smart_ptr& anotherSP) = delete; //禁止复制构造 smart_ptr& operator=(const smart_ptr& anotherSP) = delete; //禁止复制赋值 }; int main() { try { smart_ptr smartPtrSong(new Song("Nothing on You")); smartPtrSong->Play(); smart_ptr smartPtrDog(new Dog); smartPtrDog->Bark(); } catch (...){} return 0; }
unique_ptr: 适用于管理只有一个所有者的动态分配资源场合
void someFuntion()
{
unique_ptrpMc(new MyClass);
pMc->DoSomeWork();
}
unique_ptr类模板的简化定义:
templateclass unique_ptr { public: unique_ptr(T* p = nullptr); //构造函数,记住资源对象 ~unique_ptr(); //析构函数,删除资源对象 T& operator*()const; //重载解引用运算符*,非空状态才能使用 T* operator->()const; //重载选择运算符->,非空状态才能使用 unique_ptr(unique_ptr&& anotherUP); //移动构造 unique_ptr& operator=(unique_ptr&& anotherUP); //移动赋值 unique_ptr(const unique_ptr& anotherUP) = delete; //禁止赋值构造 unique_ptr& operator=(const unique_ptr& anotherUP) = delete; //禁止复制赋值 operator bool()const; //非空时为true,空时为false void reset(T* p = nullptr); //删除源资源对象,托管新对象 T* get(); //返回资源对象原始指针,托管关系不变 T* relase(); //放弃托管关系,返回资源对象原始指针,成为空状态 };
unique_ptr的一些样例片段:
unique_ptrup; //管理T类型对象的智能指针对象,处于空状态 up.reset(new T); //托管新对象 if (up) { *up; //所指对象引用,非空是才可以使用 up->member; //所指对象成员,非空是才可以使用 } p = up.get(); //获得传统“裸指针”,保留管理权 p = up.relase(); //放弃管理权 //智能指针的创建 unique_ptr u_i; u_i.reset(new int(3)); unique_ptr u_i2(new int(4)); //所有权的变化 //u_i2 = u_i; //错误,不可以重复赋值 u_i2 = std::move(u_i); //正确,可以移动赋值 int* p_i = u_i2.relase(); //放弃管理权 unique_ptr u_s(new string("abc")); //创建字符串智能指针 unique_ptr u_s2 = std::move(u_s); //移动构造 u_s2 = nullptr; //显式销毁所指对象
shared_ptr: 适用于多个对象共同拥有动态分配资源的场合
#include#include #include #include using namespace std; template void fun() { shared_ptr sp; sp.reset(new t()); if (sp) { *sp; //sp->member; } t* p = sp.get(); cout << *p << endl; } int main() { fun (); fun (); shared_ptr s_i; assert(s_i.use_count() == 0); s_i.reset(new int(0)); assert(s_i.use_count() == 1); auto s_i2 = make_shared (2); { shared_ptr s_i3(new int(3)); cout << *s_i3 << endl; s_i3 = s_i; cout << *s_i3 << endl; *s_i = 1; cout << *s_i3 << endl; assert(s_i.use_count() == 2); assert(s_i3.use_count() == 2); } assert(s_i.use_count() == 1); shared_ptr s_s(new string("abc")); shared_ptr s_s2 = s_s; cout << *s_s2 << endl; auto s_s3 = make_shared ("hello"); s_s2 = nullptr; cout << *s_s << endl; return 0; }
weak_ptr: 弱指针
weak_ptr类模板的简化定义
templateclass weak_ptr { public: weak_ptr(); //构造函数,建立空指针 explicit weak_ptr(const share_ptr & anotherSP); //建立关联共享指针的弱指针 weak_ptr& operator=(const shared_ptr & anotherSP); //更新关联的共享智能指针 weak_ptr(const weak_ptr& anotherWP); //拷贝构造 weak_ptr& operator=(const weak_ptr& anotherWP); //复制赋值 long use_const()const; //返回关联的共享智能指针的资源对象引用计数,主要用于调试 bool expored()const; //关联的共享智能指针是否过期 shared_ptr lock(); //返回关联的共享智能指针,过期时返回空状态指针 void reset(); //重置为空指针 };
说明弱指针weak_ptr常用接口使用方法的简单样例:
#include#include using namespace std; struct A { A(int iv) :m_iValue(iv) {} ~A() { cout << "A 类对象析构" << endl; } int m_iValue; }; void TestWeakPtr(weak_ptr wp) { shared_ptr sp; cout << wp.expired() << endl; cout << wp.use_count() << endl; if (sp = wp.lock()) { cout << "success, value" << sp->m_iValue << endl; } else { cout << "empty" << endl; } } int main() { shared_ptr sp1(new A(1)), sp2; weak_ptr wp1, wp2(sp1), wp3(wp2); TestWeakPtr(wp1); TestWeakPtr(wp2); TestWeakPtr(wp3); { shared_ptr sp3(new A(2)); wp3 = sp3; TestWeakPtr(wp3); wp2 = wp3; TestWeakPtr(wp2); } TestWeakPtr(wp2); return 0; }



