多维数组的理解

要清楚的理解多维数组,需要先理解指针的算术运算和数组名的含义。

1、指针的算术运算

    指针的算术运算与普通的类型的算术运算是不同的,编译器会在指针的算术运算的过程中自动乘以sizeof(type),如int p=1;p=p+2;则p=3;而int *p; (假如p指向的初始地址位2000),那么p=p+2;实际上指向的是2000+2*sizeof(int),32位系统下的结果为2008。

2、多维数组名字的理解

    对于数组名大家都知道可以理解为指针,可究竟这个指针指向的内容是什么呢?这个我没法直接说清楚,直接对着例子说吧

   如:定义了下面的一个三维数组,那么num当做指针的话它指向的内容是什么呢,其实它可以理解为只有三个元素的一维数组,num[3]={a[4][5],b[4][5],c[4][5]};而a,b,c为三个4行5列的二维数组a[4][5]={{1,2,3,4,5},{6,7,8,9,10},{11,12,13,14,15},{16,17,18,19,20}};

                                     b[4][5]={{21,22,23,24,25},{26,27,28,29,30},{31,32,33,34,35},{36,77,88,39,40}}

                                     c[4][5]={{41,42,43,44,45},{46,47,48,49,50},{51,52,53,54,55},{56,57,58,59,60}}

int num[3][4][5]={{{1,2,3,4,5},{6,7,8,9,10},{11,12,13,14,15},{16,17,18,19,20}},
                       {{21,22,23,24,25},{26,27,28,29,30},{31,32,33,34,35},{36,77,88,39,40}},
                       {{41,42,43,44,45},{46,47,48,49,50},{51,52,53,54,55},{56,57,58,59,60}}};

综上,num是一个指向{{1,2,3,4,5},{6,7,8,9,10},{11,12,13,14,15},{16,17,18,19,20}}元素的指针,而不是指向1的指针,虽然他们的地址相同,但是num+1可就不同了,根据对指针运算的理解,num+1之后num的值应为:原地址值+sizeof(num),如果上述分析正确的话,执行num+1之后,num应为:原地址值+sizeof(int)*4*5,即32为系统下num+1的值应比num的值多80,而不是4,下面通过程序验证下:

#include<iostream>
using namespace std;
int main()
{
    int num[3][4][5]={{{1,2,3,4,5},{6,7,8,9,10},{11,12,13,14,15},{16,17,18,19,20}},
                       {{21,22,23,24,25},{26,27,28,29,30},{31,32,33,34,35},{36,77,88,39,40}},
                       {{41,42,43,44,45},{46,47,48,49,50},{51,52,53,54,55},{56,57,58,59,60}}};
    int addr1=(int)num;
    int addr2=(int)(num+1);
    cout<<addr1<<endl<<addr2<<endl;
    return 0;
}

    理解上面的内容就可以对多维数组进行操作了,如定位到23这个元素,首先要先通过*(num+1)定位到{{21,22,23,24,25},{26,27,28,29,30},{31,32,33,34,35},{36,77,88,39,40}},然后在对其*()即*(*(num+1))定位到{21,22,23,24,25},然后在*(+2)即*(*(*(num+1))+2)定位到23。

3、用数组名作为一维指针去操作多维数组

    其实多维数组只是为了方便程序员编程,而设定的,在内存中多维数组就是一个一维数组,它是按照从左到右一个元素一个元素线性排列的,如上述num数组中的元素就是按照从1到60排序的。使用时需要先找到多维数组中第一个元素的地址,然后将其赋值给一维指针,如int *p=&num[0][0][0];或int *p=num[0][0];

#include<iostream>
using namespace std;
int main()
{
    int num[3][4][5]={{{1,2,3,4,5},{6,7,8,9,10},{11,12,13,14,15},{16,17,18,19,20}},
                       {{21,22,23,24,25},{26,27,28,29,30},{31,32,33,34,35},{36,77,88,39,40}},
                       {{41,42,43,44,45},{46,47,48,49,50},{51,52,53,54,55},{56,57,58,59,60}}};
    int addr1=(int)num;
    int addr2=(int)(num+1);
    cout<<addr1<<endl<<addr2<<endl;
    cout<<*(*(*(num+1))+2)<<endl;
    int *p=&num[0][0][0];
    int *q=num[0][0];
    cout<<*(p+22)<<endl;
    cout<<*(q+22)<<endl;
    return 0;
}

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

发表于

我来说两句

0 条评论
登录 后参与评论

相关文章

来自专栏SeanCheney的专栏

《利用Python进行数据分析·第2版》第3章 Python的数据结构、函数和文件3.1 数据结构和序列3.2 函数3.3 文件和操作系统3.4 结论

本章讨论Python的内置功能,这些功能本书会用到很多。虽然扩展库,比如pandas和Numpy,使处理大数据集很方便,但它们是和Python的内置数据处理工具...

4696
来自专栏debugeeker的专栏

《coredump问题原理探究》Linux x86版6.3节有成员变量的类coredump例子

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/xuzhina/article/detai...

1341
来自专栏轮子工厂

3. C语言 -- 叫你一声你敢答应嘛

\(@^0^@)/ 嗨!大家好,我是呆博~前两天的文章还满意嘛,如果有不满意的地方尽管提,我一定……嗯……能做到的我一定做。今天准备给大家分享第三篇文章,变量与...

1245
来自专栏python学习指南

python字典

本篇将介绍Python里面的字典,更多内容请参考:Python学习指南 Python是什么? Python内置了字典dict的支持,dict全称dicti...

3448
来自专栏C/C++基础

二路归并排序简介及其并行化

归并排序是分治法(Divide and Conquer)的一个典型的应用。将已有序的子序列合并,得到完全有序的序列;即先使每个子序列有序,再使子序列段间有序。若...

1171
来自专栏Crossin的编程教室

关于函数参数传递,80%人都错了

https://docs.python.org/3/faq/programming.html#how-do-i-write-a-function-with-ou...

1243
来自专栏章鱼的慢慢技术路

追踪状态——消息解码问题的思路剖析

1763
来自专栏MelonTeam专栏

OpenGL ES读书笔记(一)—初始庐山真面目

1. OpenGL ES简介 OpenGL ES(OpenGL for Embedded Systems)是以手持和嵌入式设备为目标的高级3D图形应用程序编程接...

26010
来自专栏梧雨北辰的开发录

Swift学习:泛型

本篇将详细总结介绍Swift泛型的用法; Swift泛型代码让你能够根据自定义的需求,编写出适用于任意类型、灵活可重用的函数及类型。它能让你避免代码的重复,用...

882
来自专栏IT可乐

Java数据结构和算法(十三)——哈希表

  Hash表也称散列表,也有直接译作哈希表,Hash表是一种根据关键字值(key - value)而直接进行访问的数据结构。它基于数组,通过把关键字映射到数组...

3028

扫码关注云+社区

领取腾讯云代金券