c++ primer知识点-第4章 数组和指针
目录
4.1 数组
4.2 指针的引入
4.3 C风格字符串
4.4 多维数组
4.1 数组
数组是由类型名、标识符和维数组成的复合数据类型。类型名可以是内置类型或类类型,也可以是除引用外的任意复合类型。
4.1.1 数组的定义和初始化
维数必须用值大于等于1的常量表达式定义;表达式包含整型字面值、枚举常量或者用常量表达式初始化的整型const对象。非const变量以及要到运行阶段才知道其值的const变量都不能用于定义数组的维数。
1. 显示初始化数组元素
未显式初始化的函数体外定义的内置数组,其元素初始化为0;未显式初始化的函数体内定义的内置数组,则无初始化。
int ia[] = {0, 1, 2}; // an array of dimension 3
2. 特殊的字符数组
char ca1[] = {'c', '+', '+'}; //no null char ca2[] = {'c', '+', '+', '�'}; //explit null char ca3[] = "c++"; // null terminator added automatically
3. 不允许数值直接复制和赋值
数组不能互相复制及初始化。
4.1.2 数组操作
数组下标类型:size_t 。
4.2 指针的引入
4.2.1 什么是指针?
指针保存的是一个对象的地址;当&取地址操作符作用于一个对象时,返回的是该对象的存储地址。
4.2.2 指针的定义和初始化
每个指针都有一个与之关联的数据类型,该类型决定了指针所指向的对象的类型。
1. 指针变量的定义
*符号把一个标识符声明为指针。
2. 另一种声明指针的风格
可用空格符称号*与其后的标识符分隔开来。
3. 续声明多个指针易导致混淆
string* ps1; string* ps2; // ---------> string *ps1, *ps2;
4. 指针可能的取值
5. 避免使用未初始化的指针
如果可能的话,除非所指向的对象已经存在,否则不要先定义指针,这样可避免定义一个未初始化的指针。
6. 指针初始化和赋值操作的约束
对指针进行初始化只能使用以下四种类型的值:
a.0值常量表达式
b.类型匹配的对象的地址
c.另一个对象之后的下一个地址
d.同类型的另一个有效地址
除了使用数值0或在编译时值为0的const量外,还可以使用C++语言从C语言中继承下来的预处理器变量NULL,定义于cstdlib。
7. void * 指针
void * 指针可以保存任何类型对象的地址;但仅支持几种操作:与另一指针比较;向函数传递void * 指针或从函数返回void * 指针;给另一个void * 指针赋值。
4.2.3 指针操作
*解引用操作符
1. 生成左值的解引用操作
*sp = "goodbye"; //contents of s now changed
2. 指针和引用的比较
引用总是指向某个对象;定义引用时没初始化是错误的,给引用赋值修改的是该引用所关联的对象的值。
3. 指向指针的指针
int ival = 1024; int *pi = &ival; // pi points to an int int **ppi = π //ppi points to a pointer to int
4.2.4 使用指针访问数组元素
1. 指针的算术操作
指针相减结果类型为ptrdiff_t(有正负,signed)
2. 解引用和指针算术操作之间的相互作用
int last = *(ia+4);
3. 下标和指针
int *p = iva[0]; int i = p[1]; //ok int *p = iva[2]; int i = p[-2]; //which equal iva[0]
4. 计算数组的超出末端指针
int arr[5] = [0]; int *p = arr; //arr[0] int *q = p + 5; //q is a ender
不能对q进行解引用,一般只能用于比较。
5. 输出数组元素
6. 指针是数组的迭代器
4.2.5 指针和const限定符
1. 指向const对象的指针
指向const对象的指针也必须具有const特性;指向非const对象的const指针不能通过指针修改对象,但可以通过其他方法修改。
2. const指针
指向(int)型对象的const指针:
int * const p1;
指向const对象的指针:
const int *p2;
p1不能指向别的对象,但其指向的值能否修改取决于其类型。
3. 指向const对象的const指针
const double * const pi_ptr;
不能指向另一个对象,且不能通过指针修改其指向的值。
4. 指针和typedef
typedef string *pstring; const pstring cstr; //----------> string * const cstr;
4.3 C风格字符串
C风格字符串是以空字符NULL结束的字符数组。
1. C风格字符串的使用
利用空字符作为循环条件。
2. C风格字符串的标准库函数
#include <cstring>
传递给这些标准库函数的指针必须具有非零值,并且指向以NULL结束的字符数组中的第一个元素。
操纵C风格字符串的标准库函数
| strlen(s) | 返回s的长度,不包括结束符NULL |
| strcmp(s1,s2) | 比较s1和s2是否相同,相同,返回0;s1>s2,返回正数;s1<s2,返回负数 |
| strcat(s1,s2) | 将字符串s2连接到s1后,返回s1 |
| strcpy(s1,s2) | 将s2复制给s1,返回s1 |
| strncat(s1,s2,n) | 将s2的前n个字符连接到s1后面,并返回s1 |
| strcpy(s1,s2,n) | 将s2的前n个字符复制到s1,并返回s1 |
3. 永远不要忘记字符串结束符NULL
char ca[] = {'c', '+', '+'}; //not null-terminated cout << strlen(ca) << endl; // disaster:ca isn't null-terminated
4. 调用者必须确保目标字符串具有足够大小
strcat,strcpy。
5. 使用strn函数处理C风格字符串
strncat,strncpy可以控制字符个数,但是不要忘了字符串结尾的’�’。
6. 尽可能使用标准库类型string
4.3.1 创建动态数组
1. 动态数组的定义
动态数组定义不需要为数组命名,定义后返回数组第一个元素的指针。
int *pia = new int[10]; //array of 10 uninitialized ints
其中的维数可以是任意复杂的表达式。
2. 初始化动态分配的数组
动态数值中如果元素为类类型,则使用默认构造函数,内置类型元素无初始化;可以在动态数组长度后面加一对空圆括号,对其进行初始化,但不能初始化为不同的初值。
3. const对象的动态数组
必须初始化,不允许修改,因些用处不大。
4. 允许动态分配空数组
可以分配长度为0的动态数组,但其仅支持以下操作:比较运算(不能在循环中使用);加减0,得0值。
5. 动态空间的释放
动态分配的内存必须进行释放。
delete [] pia;
6. 动态数组的使用
常常使用char*指针指向多个C风格字符串;采用这种技术比建立固定大小的数组安全。
4.3.2 新旧代码的兼容
1. 混合使用标准库类string和C风格字符串
可以把C风格字符串用在任何可以使用字符串字面值的地方:a.可以使用C风格字符串对string对象进行初始化或赋值。b.string类型可以使用C风格字符串作为加减法操作的其中一个操作数;也允许将其用作复合赋值操作的右操作数。
2. 使用数组初始化vector对象
使用数组初始化vector对象,必须指出用于初始化式的第一个元素以及数组最后一个元素的下一个位置的地址:
const size_t arr_size = 6; int int_arr[arr_size} = {0, 1, 2, 3, 4, 5}; vector<int> ivec(int_arr, int_arr + int_size);
传递给ivec的两个指针标出了vector初值的范围,被标出的元素范围可以是数组的子集。
vector<int> ivec(int_arr, int_arr + 4); //three elements
4.4 多维数组
int[2][3],第一维称为行,第二维称为列。
1. 多维数组的初始化
int ia[3][4] = {{0,1,2,3},{4,5,6,7},{8,9,10,11}};
只初始化每行的第一个元素
int ia[3][4] = {{0},{4},{8}};
2. 多维数组的下标引用
当需要访问数组中的特定元素时,必须提供其行下标和列下标。如果表达式只提供了一个下标,则结果获取的元素是该行下标索引的内层数组。
指针和多维数组
由多维数组转换而成的指针类型应是指向第一个内层数组的指针。
int *ip[4]; //array of pointers to int int (*ip)[4]; //pointers to an array of 4 ints
用typedef简化指向多维数组的指针
typedef int int_array[4]; //array of points to int int_arr *ip = ia; //points to an array of 4 ints
