摘要: 本章开始讨论内存分配的一些用法,C/C++内存分配采用new和delete。在new申请内存时,可能会遇到的一种情况就是,内存不够了,这时候会抛出out of memory的异常。有的时候,我们希望能够调用自己定制的异常处理函数,这就是本条款要说的。在声明于的一个标准程序库中,有如下的接口:1 na...阅读全文
posted @ 2014-05-11 23:15 Jerry19880126 阅读(2261) 评论(0) 编辑
摘要: 作为模板部分的结束节,本条款谈到了模板元编程,元编程本质上就是将运行期的代价转移到编译期,它利用template编译生成C++源码,举下面阶乘例子: 1 template 2 struct Factorial 3 { 4 enum 5 { 6 value = N *...阅读全文
posted @ 2014-04-17 23:03 Jerry19880126 阅读(592) 评论(0) 编辑
摘要: 这一条款主要来讨论模板中迭代器的属性iterator_category,它可以通过类似于vector::iterator::iterator_category的方式来取得。到这里我们有必要学习一下STL迭代器的类型,总共有五种,分别是:input_iterator:只读,只能逐个前移output_i...阅读全文
posted @ 2014-04-16 23:42 Jerry19880126 阅读(1150) 评论(0) 编辑
摘要: 这个条款可以看成是条款24的续集,我们先简单回顾一下条款24,它说了为什么类似于operator *这样的重载运算符要定义成非成员函数(是为了保证混合乘法2*SomeRational或者SomeRational*2都可以通过编译,2不能同时进行隐式类型转换成某个Rational,再作this用)。所以我们一般将之定义成友元函数,像下面这样: 1 class Rational 2 { 3 private: 4 int numerator; 5 int denominator; 6 public: 7 Rational(int n = 0, int d = 1): nume...阅读全文
posted @ 2014-04-08 23:59 Jerry19880126 阅读(914) 评论(1) 编辑
摘要: 比如有一个Base类和一个Derived类,像下面这样:1 class BaseClass2 {…};3 4 class DerivedClass : public BaseClass5 {…};因为是父类与子类的关系,所以可以这样写:1 DerivedClass *d;2 BaseClass *b = static_castd; // 用C风格直接是 b = (BaseClass*) d;我们可以弄一个简易的Shared型智能指针类,如果直接像下面这样写: 1 template 2 class SharedPtr 3 { 4 private: 5 T* Ptr; 6 sta...阅读全文
posted @ 2014-04-04 23:49 Jerry19880126 阅读(714) 评论(0) 编辑
摘要: 标题上说“将与参数无关的代码抽离template”,这里的参数既可以指类型,也可以是非类型,我们先来看看非类型的情况。假定我们要为矩阵写一个类,这个矩阵的行列元素个数相等,是一个方阵,因而我们可以对之求逆运算。因为方阵的元素可以有多种类型,同时方阵的维数(方阵大小)也可以不同,像下面这样,我们使用了模板: 1 template 2 class SquareMatrix 3 { 4 public: 5 void Invert(); 6 }; 7 8 int main() 9 {10 SquareMatrix a;11 SquareMatrix b;12 }模板既可以指...阅读全文
posted @ 2014-03-27 23:53 Jerry19880126 阅读(802) 评论(0) 编辑
摘要: 背景是这样的,有两个不同的公司,然后想设计一个MessageSender,为这两个公司发送不同的消息,既支持明文发送SendClearText,也支持密文发送SendEncryptedText。一种思路是采用动态绑定的方法,定义一个BasicMessageSender,里面有两个方法,分别是发送明文和密文的虚函数,然后定义它的子类MessageSenderForCompanyA,以及MessageSenderForCompanyB,在这两个子类里面覆盖发送明文和密文的虚函数,从而达到根据不同公司发送不同消息的目的。但这里我们想换一种思路,使用静态多态的方法来实现,静态多态就是模板的技术了,代码阅读全文
posted @ 2014-03-26 00:00 Jerry19880126 阅读(772) 评论(0) 编辑
摘要: 顾名思义,typename有双重含意。只要你用过template,那么第一重含意一定知道,那就是声明模板的时候,我们既可以这样写:template 也可以这样写template 这两种写法并没有任何区别,都是标记T可以是符合隐式接口的任何类型,包括系统预定义类型,也包括用户自定义类型。typename的第二重含意其实不大能遇到,因为这个依赖于编译器,看下面的例子: 1 class SampleClass 2 { 3 public: 4 typedef int MyInt; 5 // static const int MyInt = 3; 6 }; 7 8 int main() 9 {...阅读全文
posted @ 2014-03-24 23:48 Jerry19880126 阅读(1820) 评论(0) 编辑
摘要: 从本条款开始,就进入了全书的第七部分:模板与泛型编程。模板与泛型在C++中是非常重要的部分,还记得本书第一章时,把C++视为一个联邦,它由四个州政府组成,其中一个政府就是模板与泛型了。本条款是一个介绍性质的条款,内容不难,只需要讲清楚两个概念就行了,即什么是隐式接口,什么是编译期多态。隐式接口是相对于函数签名所代码的显式接口而言的。当我们看到一个函数签名(即函数声明),比如说:string GetNameByStudentID(int StudentID);我们就知道这个函数有一个整型的形参,返回值是string。但隐式接口是由有效表达式组成的,考虑一个模板函数,像下面这样:1 templat阅读全文
posted @ 2014-03-24 00:11 Jerry19880126 阅读(1207) 评论(0) 编辑
摘要: 书上类继承相关章节到这里就结束了,这里不妨说下C++内存分布结构,我们来看看编译器是怎么处理类成员内存分布的,特别是在继承、虚函数存在的情况下。工欲善其事,必先利其器,我们先用好Visual Studio工具,像下面这样一步一步来:先选择左侧的C/C++->命令行,然后在其他选项这里写上/d1 reportAllClassLayout,它可以看到所有相关类的内存布局,如果写上/d1 reportSingleClassLayoutXXX(XXX为类名),则只会打出指定类XXX的内存布局。近期的VS版本都支持这样配置。下面可以定义一个类,像下面这样:1 class Base2 {3 int.阅读全文
posted @ 2014-03-22 00:12 Jerry19880126 阅读(30153) 评论(5) 编辑