C Primer Plus(十)

第十章 数组和指针10.1 数组

数组是由一系列类型相同的元素构成。数组声明中包括数组元素的数目和元素的类型。

10.1.1 初始化

有时需要使用只读数组,也就是程序从数组中读取数值,但是程序不向数组中写数据。在这种情况下,初始化的时候可以使用关键字const。与普通变量相似,在初始化之前数组元素的数值是不定的。当数值数目少于数组元素数目时,多余的数组元素被初始化为0。如果不初始化数组,数组元素和未初始化的普通变量一样,其中存储的是无用的数值;但是如果部分初始化数组,未初始化的元素则被设置为0。如果初始化列表中的项目个数大于数组大小,编译器会认为这是一个错误。您可以省略括号中的数字,从而让编译器自动匹配数组大小和初始化列表中的项目数目。

由于人工计算容易出错,可以让计算机来计算数组的大小。运算sizeof给出其后的对象或类型的大小。sizeof days是整个数组的大小(以字节为单位),sizeof days[0]是一个元素的大小。

10.1.2 指定初始化项目(C99)

此特性允许选择对某些元素进行初始化。例如:int arr[6]={[5]=212};程序如下:

#include<stdio.h>#define MONTHS 12int main(void){int days[MONTHS]={31,28,[4]=31,30,31,[1]=29};int index;for(index=0;index<MONTHS;index++)printf(“month %2d has %d days.\n”,index+1,days[index]);return 0;}

如果多次对一个元素进行初始化,则最后的一次有效。C不支持把数组作为一个整体来进行赋值,也不支持用花括号起来的形式进行赋值(初始化的时候除外)。注意使用数组的时候,索引不能超过数组的边界。编译器不检查索引的合法性。不检查边界能够让C程序的运行速度更快。声明数组时在方括号内只能使用整数常量表达式。sizeof表达式被认为是一个整数常量,而一个const值却不是整数常量。并且该表达式的值必须大于0。C99引入变长数组主要是为了使C更适于做数值计算。

10.2 多维数组

二维数组的声明方法:float rain[5][12];rain是一个包含5个元素的数组,每个元素的类型是float[12];rain[0][0]是一个float数。也可以把rain看作是一个二维数组,它包含有5行,每行12列。改变第二个下标,可以沿着一行移动,改变第一个下标,可以沿着一列垂直移动。初始化二维数组可以例如float[5][12]={{…..},{…..},{…..},{…..},{…..}};每个数值列表都用花括号括起来。第一个列表给赋值给数组的第一行。初始化时候也可以省略内部的花括号,只保留最外面的一对花括号。只要保证数值的个数正确,若不够,则后面的元素被初始化为0。同样适用于三维数组。

10.3 指针和数组

数组标记实际上是一种变相使用指针的形式。数组名同时也是该数组首元素的地址。如果fizny是一个数组,则finzy==&finzy[0];两者都是常量。在C中对一个指针加1的结果是对该指针增加1个存储单元(它指向的对象的字节大小)。对于数组而言,地址会增加到下一个元素的地址,而不是下一个字节。finzy+2==&finzy[2];*(finzy+2)==finzy[2];注意区分*(finzy+2)和*finzy+2:间接运算符*的优先级高于+,因此后者等价于:*(finzy)+2,网站空间,前者为数组第三个元素的值。在函数原型中,可以用int *ar代替 int ar[];将数组名传递给函数的形参时,数组大小无法得知。可以有两种方法结解决1.在函数代码中协商固定的数组大小。2.把数组大小作为第二个参数传递给函数。原型允许省略名称,定义函数时不可以省略。

10.3.1 使用指针参数

向函数传递数组信息时,可以传递两个指针,一个指明数组的起始地址,一个指明数组的结束地址。例如

end实际指向的位置实在数组最后一个元素之后。C保证在为数组分配存储空间的时候,指向数组之后的第一个位置的指针也是合法的。*start++:一元运算符*和++具有相等的优先级,但它在结合时是从右向左进行的。尽管*start++合法,但为了清晰起见应该使用*(start++)。只有当start是指针变量时,才可以使用++这样的表达式。

10.4 指针操作

下面例举了可对指针变量执行的基本操作:赋值—-可以把一个地址赋给指针。通常用数组名或地址运算符&来进行地址赋值。(地址应该和指针类型兼容)求值—-运算符*可取出指针指向地址中存储的数值。取指针地址—-指针变量同其它变量一样具有地址和数值,使用运算符&可以得到存储指针本身的地址。将一个整数加给指针—-整数会和指针所指类型的字节数相乘,然后所得的结果会加到初始地址上。增加指针的值—-可以通过一般加法或增量运算符来增加一个指针的值。从指针中减去一个数—-指针必须是第一个操作数,或者是一个指向整数的指针。减小指针的值—-指针可以做减量运算。求差值—-通常对分别指向同一个数组内两个元素的指针求差值,以求出元素之间的距离,差值的单位是相应类型的大小。比较—-前提是两个指针具有相同的类型。C保证指向数组元素的指针和指向数组后的第一个地址的指针是有效的。但如果指针超出了这个范围,后果将是未知的。不能对未初始化的指针取值。这样的话可能会覆盖程序数据或者代码,甚至导致程序的崩溃。当创建一个指针时,系统只飞陪了用来存储指针本身的内存空间,并把分配用来存储数据的内存空间。

10.5 保护数组内容

因为向函数传递的是数组,可能会破坏原始数据的完整性。为此,可以在函数原型和定义的形式参量声明中使用关键字const。

10.5.1 有关const的其它内容

指向常量的指针不能用于修改数值。double rates[5]={88.99,100.12,59.45,183.11,340.5};const double *pd=rates;*pd=29.89; //不允许pd[2]=222.22; //不允许rates[0]=99.99; //允许pd++ //允许将常量或非常量数据的地址赋给指向常量的指针是合法的。只有非常量数据的地址才可以赋给普通的指针,否则,您就可以使用指针来修改被认为是常量的数据。const double locked[4]={0.08,0.075,0.0725,0.07}; double *pnc; pnc=locked; //非法的

当你能梦的时候就不要放弃梦

C Primer Plus(十)

相关文章:

你感兴趣的文章:

标签云: