sizeof辨析——二维数组(超级详细)

2024-03-10 05:20

本文主要是介绍sizeof辨析——二维数组(超级详细),希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

二维数组加sizeof的知识如果基础不扎实,上面的代码恐怕很难区分,这篇文章就深度解析一下有关问题

我们在分析之前,要提及一些基础的前提知识

前提知识:

一:

&数组名 和 sizeof(数组名)这两个例外中,数组名代表整个数组

除此之外所有的数组名都是表示首元素的地址

二:

我们直观以为的二维数组储存方式

实际计算机二维数组储存方式

也就是说:它们之间的地址是连续的!

三:

公式:    *(数组名+自然数)== 数组名[自然数]

例如:

*(arr+1)==arr[1]

四:

地址的大小分环境,如果在x86(也就是32位环境下),大小为4个字节

如果在x64(也就是64位环境下),大小为8个字节

五:

sizeof()的()中的不参与编译运算

小练习

分析之前我们先来尝试思考一些简单一点的问题,避免一上来分析题目犯迷糊,容易绕晕

int arr[3][4]

第一类:

sizeof(arr) 

sizeof(arr[0])

sizeof(arr[0][0])

很简单吧,首先上面这三个都符合前提知识的第一条,所以这些数组名都代表整个数组

arr代表的是整个二维数组,所以sizeof(arr)就代表整个二维数组的大小,就是3*4*4=48字节(因为int类型大小为4个字节)

arr[0]代表的是在二维数组中,第一行的一维数组,所以sizeof(arr[0])也就是整个第一行的大小,就是4*4=16字节

arr[0][0]代表的是在二维数组中,第一行的一维数组中的第一个元素,所以sizeof(arr[0][0])就代表该元素的大小,就是4个字节

第二类:

sizeof(arr+1)

sizeof(&arr+1)

在这一类中,sizeof(arr+1)格式为sizeof(数组名+1),而不为sizeof(数组名),所以这里的arr不属于两个例外,即不是代表整个数组,而是首元素地址

又因为二维数组的首元素地址为arr[0],所以此时arr就相当于第一行的一维数组的起始地址,所以arr+1为第二行的一维数组的起始地址,因为是地址,所以大小为4或者8字节

如果有点迷糊的话,可以这么简单理解:

二维数组分为三个层次

最高层次:二维数组

中间层次:一维数组

最低层次:一维数组的元素

而首元素地址就相当于降一级(也就是不符合sizeof(数组名)和&(数组名)格式的降级)

二维数组的首元素地址就为第一行的一维数组的起始地址

一维数组的首元素地址就为第一个元素的地址

然后sizeof(&arr+1)格式为sizeof(&(数组名)+1),虽然不符合sizeof(数组名)的格式,但是符合&(数组名)的格式,所以这里的arr代表整个二维数组,二维数组加1就相当于跳过整个二维数组,来到最后一行的一维数组的最后一个元素后面的那个地址,因为是地址,所以大小为4或者8字节

分析题目

1.  sizeof(a),符合格式sizeof(数组名),所以这里的a代表整个二维数组,所以为3*4*4=48字节

(起始a为最高层次)

2.  sizeof(a[0][0]),这里a[0][0]代表二维数组中第一行的一维数组的第一个元素,所以为4个字节

(起始a[0][0]为最低层次)

3.  sizeof(a[0]),符合格式sizeof(数组名),所以这里a[0]代表二维数组中第一行的整个一维数组,所以为4*4=16字节

(起始a[0]为中间层次)

4.  sizeof(a[0]+1),这里a[0]+1不符合sizeof(数组名)的格式,所以这里的a[0]代表二维数组中第一行一维数组的首元素地址,又因为我们说过首元素地址相当于降一级,所以a[0]代表了二维数组中第一行一维数组的第一个元素的起始地址,a[0]+1就是第一行的一维数组的第二个元素的地址,因为是地址,所以为4或者8字节

(起始a[0]为中间层次,首元素降级变为最低层次)

5.  sizeof( * (a[0]+1) ),根据前提知识的第三条的公式可知, * (a[0]+1)  == a[0][1],代表二维数组中第一行的一维数组的第二个元素,所以为4个字节

(起始a[0]为中间层次,首元素降级变为最低层次)

6.  sizeof(a+1),不符合sizeof(数组名)的格式,所以这里的a代表二维数组的首元素地址,又因为我们说过首元素地址相当于降一级,所以a代表了二维数组中第一行的一维数组的起始地址,则a+1代表二维数组中第二行的一维数组的起始地址,所以为4或者8字节

(起始a为最高层次,首元素降级变为中间层次)

7.  sizeof( *(a+1) ),根据前提知识的第三条的公式可知,*(a+1) ==  a[1],代表二维数组中第二行的整个一维数组,所以大小为4*4=16字节

(起始a为最高层次,首元素降级变为中间层次)

8.  sizeof( &a[0]+1 ),符合&(数组名)的格式,所以这里的a[0]代表二维数组中第一行的整个一维数组,&a[0]就为二维数组中第一行的一维数组的起始地址,&a[0]+1代表二维数组中第二行的一维数组的起始地址,因为是地址,所以为4或者8个字节

(起始a[0]为中间层次,因为符合&(数组名),所以没有降级,还是中间层次)

9.  sizeof( *(&a[0]+1 )),(&a[0]+1 )与上面分析一样,所以解引用后表示二维数组中第二行的整个一维数组,所以为4*4=16字节

(起始a[0]为中间层次,因为符合&(数组名),所以没有降级,还是中间层次)

10.  sizeof(*a),不符合sizeof(数组名)的格式,所以这里的a代表二维数组的首元素地址,又因为我们说过首元素地址相当于降一级,所以a代表了二维数组中第一行的一维数组的起始地址,解引用后表示二维数组中第一行的整个一维数组,所以为4*4=16字节

(起始a为最高层次,首元素降级变为中间层次)

11. sizeof(a[3]),虽然二维数组为a[3][4],不存在a[3],但是我们前提知识的第五条说过,()中的不参与编译运算,所以我们编译运行时也不会报错,计算机可以通过我们定义的二维数组类型推断出长度,符合sizeof(数组名)的格式,所以a[3]代表二维数组中第四行的整个一维数组,所以为4*4=16字节

(起始a[0]为中间层次)

这篇关于sizeof辨析——二维数组(超级详细)的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/793178

相关文章

Git打标签从本地创建到远端推送的详细流程

《Git打标签从本地创建到远端推送的详细流程》在软件开发中,Git标签(Tag)是为发布版本、标记里程碑量身定制的“快照锚点”,它能永久记录项目历史中的关键节点,然而,仅创建本地标签往往不够,如何将其... 目录一、标签的两种“形态”二、本地创建与查看1. 打附注标http://www.chinasem.cn

线上Java OOM问题定位与解决方案超详细解析

《线上JavaOOM问题定位与解决方案超详细解析》OOM是JVM抛出的错误,表示内存分配失败,:本文主要介绍线上JavaOOM问题定位与解决方案的相关资料,文中通过代码介绍的非常详细,需要的朋... 目录一、OOM问题核心认知1.1 OOM定义与技术定位1.2 OOM常见类型及技术特征二、OOM问题定位工具

基于 Cursor 开发 Spring Boot 项目详细攻略

《基于Cursor开发SpringBoot项目详细攻略》Cursor是集成GPT4、Claude3.5等LLM的VSCode类AI编程工具,支持SpringBoot项目开发全流程,涵盖环境配... 目录cursor是什么?基于 Cursor 开发 Spring Boot 项目完整指南1. 环境准备2. 创建

JavaScript中比较两个数组是否有相同元素(交集)的三种常用方法

《JavaScript中比较两个数组是否有相同元素(交集)的三种常用方法》:本文主要介绍JavaScript中比较两个数组是否有相同元素(交集)的三种常用方法,每种方法结合实例代码给大家介绍的非常... 目录引言:为什么"相等"判断如此重要?方法1:使用some()+includes()(适合小数组)方法2

Python与MySQL实现数据库实时同步的详细步骤

《Python与MySQL实现数据库实时同步的详细步骤》在日常开发中,数据同步是一项常见的需求,本篇文章将使用Python和MySQL来实现数据库实时同步,我们将围绕数据变更捕获、数据处理和数据写入这... 目录前言摘要概述:数据同步方案1. 基本思路2. mysql Binlog 简介实现步骤与代码示例1

基于C#实现PDF转图片的详细教程

《基于C#实现PDF转图片的详细教程》在数字化办公场景中,PDF文件的可视化处理需求日益增长,本文将围绕Spire.PDFfor.NET这一工具,详解如何通过C#将PDF转换为JPG、PNG等主流图片... 目录引言一、组件部署二、快速入门:PDF 转图片的核心 C# 代码三、分辨率设置 - 清晰度的决定因

Java中HashMap的用法详细介绍

《Java中HashMap的用法详细介绍》JavaHashMap是一种高效的数据结构,用于存储键值对,它是基于哈希表实现的,提供快速的插入、删除和查找操作,:本文主要介绍Java中HashMap... 目录一.HashMap1.基本概念2.底层数据结构:3.HashCode和equals方法为什么重写Has

Java使用正则提取字符串中的内容的详细步骤

《Java使用正则提取字符串中的内容的详细步骤》:本文主要介绍Java中使用正则表达式提取字符串内容的方法,通过Pattern和Matcher类实现,涵盖编译正则、查找匹配、分组捕获、数字与邮箱提... 目录1. 基础流程2. 关键方法说明3. 常见场景示例场景1:提取所有数字场景2:提取邮箱地址4. 高级

Unity新手入门学习殿堂级知识详细讲解(图文)

《Unity新手入门学习殿堂级知识详细讲解(图文)》Unity是一款跨平台游戏引擎,支持2D/3D及VR/AR开发,核心功能模块包括图形、音频、物理等,通过可视化编辑器与脚本扩展实现开发,项目结构含A... 目录入门概述什么是 UnityUnity引擎基础认知编辑器核心操作Unity 编辑器项目模式分类工程

Springboot项目构建时各种依赖详细介绍与依赖关系说明详解

《Springboot项目构建时各种依赖详细介绍与依赖关系说明详解》SpringBoot通过spring-boot-dependencies统一依赖版本管理,spring-boot-starter-w... 目录一、spring-boot-dependencies1.简介2. 内容概览3.核心内容结构4.