当前位置: 首页 > news >正文

C++ Primer:3.6 多维数组

其他章节:C++ Primer 学习心得

多维数组是数组的数组。
一个数组的元素仍然是数组时,通常用两个维度来定义:一个维度表示数组本身的大小,另外一个维度表示其元素(数组)的大小。

int ia[3][4]; // 大小为3的数组,每个元素是含有4个整数的数组
// 大小为10的数组,它的每个元素都是大小为20的数组,
// 这些数组的元素是含有30个整数的数组
int arr[10][20][30] = {0}; //将所有元素初始化为0

定义数组时对下标运算符的数量没有限制。
对于二维数组来说,把第一个维度称作行,第二个维度称作列。

多维数组的初始化

使用花括号括起来一组值初始化数组。

int ia[3][4] = {{0, 1, 2, 3},{4, 5, 6, 7},{8, 9, 10, 11}
};

其中嵌套着的花括号并非必需的。

int ia[3][4] = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11};

在初始化多维数组时也并非所有元素的值都必须包含在初始化列表内。

int ia[3][4] = {{ 0 }, { 4 }, { 8 }};
// 显式地初始化每行的首元素,未列出的元素执行默认初始化
int ix[3][4] = {0, 3, 6, 9};
// 显式地初始化第1行,其他元素执行值初始化,被初始化为0。

多维数组的下标引用

使用下标运算符访问多维数组的元素,数组的每个维度对应一个下标运算符。
如果表达式含有的下标运算符数量和数组的维度一样多,该表达式的结果将是给定类型的元素;反之,如果表达式含有的下标运算符数量比数组的维度小,则表达式的结果将是给定索引处的一个内层数组:

// 用arr 的首元素为ia最后一行的最后一个元素赋值
ia[2][3] = arr[0][0][0];
int (&row)[4] = ia[1]; // 把row绑定到ia的第二个4元素数组上

程序经常会用到两层嵌套的for循环来处理多维数组的元素

constexpr size_t rowCnt = 3, colCnt = 4;
int ia[rowCnt][colCnt]; //12 个未初始化的元素
// 对于每一行
for (size_t i = 0; i != rowCnt; ++i)//对于行内的每一列for (size_t j = 0; j != colCnt; ++j)// 外层for循环遍历ia的所有元素;内层for循环遍历一维数组的整数元素

使用范围for语句处理多维数组

C++11新增了范围for语句:

for (auto &row: ia)     // 对于外层数组的每一个元素for(auto &col: row){ // 对于内层数组的每一个元素

要改变数组的值,选用引用类型rowcol作为循环控制变量。

for (const auto &row: ia) // 对于外层数组的每一个元素for(auto col:row) //对于内层数组的每一个元素

即使循环中没有任何写操作,还是将外层循环的控制变量声明成引用类型,避免数组被自动转换为指针。


使用范围for语句处理多维数组,除了最内层的循环外,其他所有循环的控制变量都应该是引用类型。

指针和多维数组

程序使用多维数组的名称时,也会自动将其转换成指向数组首元素的指针。
多维数组实际上是数组的数组,多维数组名称转换得来的指针实际上是指向第一个内层数组的指针:

int ia[3][4];  // 大小为3的数组,每个元素是含有4个整数的数组
int (*p)[4] = ia;  // p指向含有4个整数的数组
p = &ia[2];   // p指向ia的尾元素

通过auto或者decltype就能尽可能地避免在数组前面加上一个指针类型:

//输出ia中每个元素的值,每个内层数组各占一行
//p指向含有4个整数的数组
for (auto p = ia; p != ia + 3; ++p)//q指向4个整数数组的首元素,也就是说,q指向一个整数for (auto q = *p; q != *p + 4; ++q)cout<< *q:

使用标准库函数beginend也可以实现同样的功能:

//p指向 ia的第一个数组
for (auto p = begin(ia); p != end(ia); ++p)//g指向内层数组的首元素for (auto q = begin(*p); q!= end(*p); ++q)cout << *q;//输出q所指的整数值

类型别名简化多维数组的指针

读、写和理解一个指向多维数组的指针是复杂的工作,使用类型别名可以简化这项工作。

using int_array = int[4];
typedef int int_array[4]; // 等价
//输出ia中每个元素的值,每个内层数组各占一行
for (int_array *p = ia; p != ia + 3; ++p)for (int *q = *p; q != *p + 4; ++q)cout << *q;

程序将类型“4个整数组成的数组”命名为int_array,用类型名int_array 定义外层循环的控制变量让程序显得简洁明了。

相关文章:

  • 人工智能前沿讲座——融合知识的自然语言处理
  • 用python写一个爬虫,爬取google中关于蛇的照片
  • OpenLayers学习笔记-点位聚合
  • python爬虫豆瓣电影TOP250
  • FakeNewsGPT4:通过知识增强的大规模视觉语言模型推进多模态假新闻检测
  • Python和C++骨髓细胞进化解析数学模型
  • prometheus+grafana应用监控配置
  • 基于springboot+vue+uniapp的超市购物系统小程序
  • 【Java--数据结构】二叉树oj题(上)
  • Nuxt.js头部魔法:轻松自定义页面元信息,提升用户体验
  • LeetCode 92. 反转链表 II
  • Hi3861 OpenHarmony嵌入式应用入门--华为 IoTDA 设备接入
  • 堆、栈和队列(数据结构)
  • PGCCC|【PostgreSQL】PCA+PCP+PCM等IT类认证申报个税退税指南
  • 【mysql】02在ubuntu24安装并配置mysql
  • 《Javascript数据结构和算法》笔记-「字典和散列表」
  • Apache的80端口被占用以及访问时报错403
  • CSS魔法堂:Absolute Positioning就这个样
  • Javascript弹出层-初探
  • Linux各目录及每个目录的详细介绍
  • mongo索引构建
  • nodejs调试方法
  • PermissionScope Swift4 兼容问题
  • Redis在Web项目中的应用与实践
  • SSH 免密登录
  • 从零开始在ubuntu上搭建node开发环境
  • 番外篇1:在Windows环境下安装JDK
  • 记一次删除Git记录中的大文件的过程
  • 开源中国专访:Chameleon原理首发,其它跨多端统一框架都是假的?
  • 入门级的git使用指北
  • 适配iPhoneX、iPhoneXs、iPhoneXs Max、iPhoneXr 屏幕尺寸及安全区域
  • 数据结构java版之冒泡排序及优化
  • 想使用 MongoDB ,你应该了解这8个方面!
  • 小程序01:wepy框架整合iview webapp UI
  • 小李飞刀:SQL题目刷起来!
  • 如何通过报表单元格右键控制报表跳转到不同链接地址 ...
  • 新年再起“裁员潮”,“钢铁侠”马斯克要一举裁掉SpaceX 600余名员工 ...
  • ​MySQL主从复制一致性检测
  • #中国IT界的第一本漂流日记 传递IT正能量# 【分享得“IT漂友”勋章】
  • (06)Hive——正则表达式
  • (1)Nginx简介和安装教程
  • (26)4.7 字符函数和字符串函数
  • (Redis使用系列) Springboot 使用redis实现接口幂等性拦截 十一
  • (WSI分类)WSI分类文献小综述 2024
  • (全注解开发)学习Spring-MVC的第三天
  • (转)Android学习笔记 --- android任务栈和启动模式
  • (转)创业家杂志:UCWEB天使第一步
  • *_zh_CN.properties 国际化资源文件 struts 防乱码等
  • . ./ bash dash source 这五种执行shell脚本方式 区别
  • .NET COER+CONSUL微服务项目在CENTOS环境下的部署实践
  • .NET Core跨平台微服务学习资源
  • .net 提取注释生成API文档 帮助文档
  • .NET6 命令行启动及发布单个Exe文件
  • .Net的DataSet直接与SQL2005交互
  • .net实现客户区延伸至至非客户区