C专家编程 十二 C语言的多维数组

有些人声称C语言没有多维数组,这是不对的。ANSI C标准在第6.5.4.2节以及第69号脚注上表示:

当几个“[]”修饰符连续出现时(方括号里面是数组的范围),就是定义一个多维数组。

        但所有其他语言都把这称为“数组的数组”

        C语言的方法多少有点独特:定义和引用多维数组惟一的方法就是使用数组的数组。尽管C语言把数组的数组当作是多维数组,但不能把几个下标范围如[i][j][k]合并成Pascal式的下标表达式风格如[i,j,k]。如果你清楚地明白自己在做什么,也介意产生不合规范的程序,可以把[i][j][k]这样的下标值计算为相应的偏移量,然后只用一个单一的下标[Z]来引用数组。当然这不是一种值得推荐的做法。同样糟糕的是,像[i,j,kl这样的下标形式(由逗号分隔)是C语言合法的表达形式,只是它并非同时引用这儿个下标(它实际上所引用的下标值是k, 也是就逗号表达式的值)。C语言支持其他语言一般称作“数组的数组”的东西,但却称它为多维数组,这样就模糊了两者的边界,使许多人对两者混淆不清。


        尽管术语上称作“多维数组”,但C语言实际上只支持“数组的数组”。如果在你的思维 模式中,把数组看作是一坤向量(即某种对象的一维数组,它的元素可以是另一个数组),就能极大简化编程语言中这个相当复杂的领域。

如何分解多维数组

必须仔细注意多维数组是如何分解为几个单独的数组的。如果我们声明如下的多维数组:

int apricot [21 [3 j [5];

可以按图9-8所示的任何一种方法为它在内存中定位

int apricot[2] [3] 15];


        正常情况下,赋值发生在两个相同的类型之间,如int与int、double与double等。在图 9-8中,可以看到在“数组的数组的数组”中的每一个单独的数组都可以看作是一个指针。 这是因为在表达式中的数组名被编译器当作“指向数组第一个元素的指针”(第242页的规则 1)。换句话说,不能把一个数组赋值给另一个数组,因为数组作为一个整体不能成为赋值的 对象。可以把数组名赋值给一个指针,就是因为这个“在表达式中的数组名被编译器当作一 个指针”的规则。
         指针所指向的数组的维数不同,其区别会很大。使用上面例子中的声明:
 r++;
 t++;
        将会使r和t分别指向它们各自的下一个元素(两者所指向的元素本身都是数组)。它们所增长的步长是很不相同的,因为r所指向的数组元素的大小是t所指向的数组的元素大小的三倍。

内存中数组是如何布局的

        在C语言的多维数组中,最右边的下标是最先变化的,这个约定被称为“行主序”。由 于“行/列主序”这个术语只适用于恰好是二维的多维数组,所以更确切的术语是“最右的下 标先变化”。绝大部分语言都采用了这个约定,但Fortran却是一个主要的例外,它采用了“最左的下标先变化”,也就是“列主序”。在不同的下标变化约定中,多维数组在内存中的布局也不相同。事实上,如果把一个C语言的矩阵传递给一个Fortran程序,矩阵就会被自动转置——这是一个非常厉害的邪门密技,偶尔真还会用到。


       C语言中多维数组最大的用途是存储多个字符串。有人指出“最右边的下标先变化”在 这方面具有优势(每个字符串中相邻的字符在内存中也相邻存储)。但在“最左边的下标先变化”的多维数组(如Fortran)中,情况并不如此。

如何对数组进行初始化

        在最简单的情况下,一维数组可以通过把初始值都放在一对花括号内来完成初始化。如果在数组的定义里未标明它的长度,C语言约定按照初始化值的个数来确定数组的长度。

f1oat banana[5] = { 0.0, 1.0, 2.72, 3.14, 25.625 };

float honeydew [ ] = { 0.0, 1,0, 2.12, 3.14, 25.625 };

       只能够在数组声明时对它进行整体的初始化。之所以存在这个限制,并没得过硬的理由。 多维数组可以通过嵌奪的花括号进行初始化:

short cantaloupe[2][5] = {

{10, 12, 3, 4, -5},

{3.0, 22, 6, 0, -5},

};

int rhubarb[] [3]={ 

{0, 0, 0}, 

{1, 1, 1},

};

        注意,可以在最后一个初始化值的后面加一个逗号,也可以省略它。同时,也可以省略最左边下标的长度(也只能是最左边的下标),编译器会根据初始化值的个数推断出它的长度。

        如果数组的长度比所提供的初始化值的个数要多,剩余的几个元素会自动设置为0。如果元素的类型是指针,那么它们被初始化为NULL;如果元素的类型是float,那么它们被初 始化为0.0。在流行的IEEE 754标准浮点数实现中(IBM PC和Sun系统都使用了这个标准),
0.0和0的位模式是完全一祥的。

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值