C++ Primer chap8
1 .
头文件不应该含有非inline 函数或对象的定义 例如 下面的代码表示
的正是这样的定义 因此不应该出现在头文件中
extern int ival = 10;
double fica_rate;
extern void dummy() {}
虽然ival 是用extern 声明的 但是它的显式初始化使得它实际上是个定义 类似的情况
虽然dummy()显式地声明为extern 但是空花括号代表该函数的定义 尽管fica_rate 没有被
显式地初始化 但是因为缺少extern 因而也被视为C++中实际的定义 这些定义如果在同
一程序的两个或多个文件中被包含 就会产生重复定义的编译错误
2 .
new 表达式也可以在空闲存储区中分配数组 在这种情况下 new 表达式中的类型指示
符后面必须有一对方括号 里面的维数是数组的长度 且该组数可以是一个复杂的表达式
new 表达式返回指向数组第一个元素的指针 例如
// 分配单个 int型的对象
// 用 1024 初始化
int *pi = new int( 1024 );
// 分配一个含有 1024个元素的数组
// 未被初始化
int *pia = new int[ 1024 ];
// 分配一个含 4x1024 个元素的二维数组
int (*pia2)[ 1024 ] = new int[ 4 ][ 1024 ];
3 .
我们可以使用new 表达式在空闲存储区内创建一个const 对象 如下所示
const int *pci = new const int(1024);
在空闲存储区创建的const 对象有一些特殊的属性 首先 const 对象必须被初始化 如
果省略了括号中的初始值 就会产生编译错误 除此之外 对于具有缺省构造函数的class
类型的对象 初始值可以省略 第二 用 new 表达式返回的值作为初始值的指针必须是一
个指向const 类型的指针 在前面的例子中 pci 是一个指向const int 的指针类型 它指向由
new 表达式分配的const int 对象.
所有在空闲存储区内被创建的const 对
象都必须被初始化 而且 因为const 数组不能被初始化 除了类数组 所以试图用new
表达式创建一个内置类型的const 数组会导致编译错误
const int *pci = new const int[100]; // 错误
4
定位 new 表达式
new 表达式的第三种形式可以允许程序员要求将对象创建在已经被分配好的内存中 这
种形式的new 表达式被称为定位new 表达式 placement new expression 程序员在new 表
达式中指定待创建对象所在的内存地址 new 表达式的形式如下
new (place_address) type -specifier
place_address 必须是个指针 为了使用这种形式的new 表达式 我们必须包含头文件
<new> 这项设施允许程序员预分配大量的内存 供以后通过这种形式的new 表达式创建对
象 例如
#include <iostream>
#include <new>
const int chunk = 16;
class Foo {
public:
int val() { return _val; }
Foo() { _val = 0; }
private:
int _val;
};
// 预分配内存 但没有 Foo对象
char *buf = new char[ sizeof(Foo) * chunk ];
int main() {
// 在 buf中创建一个 Foo对象
Foo *pb = new (buf) Foo;
// 检查一个对象是否被放在 buf中
if ( pb->val() == 0 )
cout << "new expression worked!" << endl;
// 到这里不能再使用 pb
delete[] buf;
return 0;
}