C/C++没有数组

在其它高级语言里,不管是定义(声明)还是引用, a[i] 或 a[3] 都是一个整体。在 C/C++ 里,却是一个表达式: a[i] 是运算符 [] 连接两个实体 a 和 i 。

说 C/C++ 并没有数组 , 有以下几条理由。

理由一: C 里没有数组形式。

“数组”名 a 本身就是一个指针,与常规指针不同的是,它是一个不能移动的所谓常指针。

如在函数外有定义:

float a[3] = {1.0, 2.0, 3.0};

首先在初始化数据段分配一块能容纳三个 float 数的空间,并填入三个初始值,然后定义一个名为 a 指向 float 数据流的常指针,并使其指向该区域的首字节。

理由二:“数组”的定义,其实最终是对指针的定义。

说“指向 float 数据流”,和说“指向 float 型数组”,是两个概念。共性是,计算偏移量(我不说移动,因为常指针是不能移动的。)时,计算单位都是 float 型数据的字节数。但是,数组是有边界的,你的下标不能超出边界。而偏移量可以超出数据流的边界(后果自负)。

很多书里说, C “数组”没有边界检查,是为了运行效率。但是,对边界的检查,系统开销并不大。 C 里的“数组”其实是个数据流,它的边界只有一头:常指针所指向的下边界。

理由三:数组名和下标竟然可以互换。

我们要访问上面那个数据流的第 2 个数据,可以使用 a[1] ,也可以使用 *(a + 1) 。两者完全等价。我怀疑, C 的作者所提供的 a[i] ,仅仅是 *(a + i) 的同义词。按照加法交换率,显然, *(a + i) 等于 *(i + a) 。那 i[a] 是不是也等于 a[i]呢?测试结果:等于。更奇怪的是,不但 i[a] 等于 a[i] , 1[a] 也等于 a[1] !

看看下面的相等关系:

a[1] 等于 *(a + 1) 等于 *(1 + a) 等于 1[a]

上面的怀疑或许有点道理了。

理由四: a[i] 无非是 *(a + i) 的同义词。

对“数组”的访问,最终总是通过指针的。其基本形式是: *(a + i) 。

“数组”名是一个常指针,总是指向该区域的首址。“下标”其实是一个逻辑偏移量。说它是“逻辑”的,意思是在计算时,需要乘以步长(数据的长度)。但是,这个“乘法”对你是透明的,不必关心它。指向所访问数据的是常指针“加”偏移量。

在 X86 系列 CPU 的指令系统里,有一个基址变址寻址方式。这种寻址方式和 C 对“数组”的访问方式很相似。常指针相当于基址,偏移量相当于变址。

我怀疑,这个基址变址寻址方式是为 C 访问“数组”而增加的。

理由五: C “数组”没有上边界。

对下面的定义

float a[3] = {1.0, 2.0, 3.0};

我们不仅可以访问 a[0] 、 a[1] 和 a[2] ,还可以访问 a[3] 、 a[4] 等。 C 数组不知道自己的一亩三分到哪里为止。用C/C++ 开发,与用其它语言不同,编程员必须记住自己定义的数组有多大。自己的家没有栅栏,跑到邻居割韭菜没人管,但后果自负。


理由六:对“多维数组”的访问总是可化解成对“一维数组”的方式。

诚然,不管是用哪种语言编程,最终生成的目的码中,数组总是被转换成一块连续的存储区(即它是线状的)。不同的是,在 C 源码里,所有的数组,不管是几维的,都是线状的。在源码层面,都可以看作是一维的。定义了

int a[3][4];

可以用 a[2][3] ,也可以用 a[11] 访问其第 2 行、第 3 列元素。

结论

C 里使用下标运算符 [] ,无非是使指向一串等类型元素的指针对该区域的操作看起来像操作数组而已。没有这东西,习惯了其它高级语言数组操作的编码员会觉得不习惯。

c/c++中索引超出数组边界问题相关推荐

  1. Matlab中出现“位置1处的索引超出数组边界(不能超过1)”

    我是一个matlab小白,前几天刚准备学习机器学习的相关知识,但是下面的代码一直提示我"位置1处的索引超出数组边界(不能超过1)". 好像出错在71行的"ans(j,:) ...

  2. matlab处理数据,提示“提示位置1处的索引超出数组边界。不能超出1”,这该怎么处理呢

  3. 求助:matlab报错:位置 2 处的索引超出数组边界(1)

    代码 clear all; %clc; I=eye(3); K=2; M=eye(3);N=eye(3); qd=[0 0 0]'; qd0=1;%期望四元数 Wd=[0 0 0]';%期望角速度%- ...

  4. 位置2处的索引超过边界总数matlab,位置 2 处的索引超出数组边界(不能超出 2)。...

    想使用fmincon函数优化求微分方程的参数,写完程序之后提示这个错误,大佬们能不能帮我看看哪里错了? 也帮忙看一下我写的程序对不对,有没有有需要改正的地方. k0=[0.023 0.000613 0 ...

  5. matlab报错:位置 2 处的索引超出数组边界(不能超出 3)。

    原因: for i=1:1:a     jieguo_data(i,1)=xingzuo_data(i,1);     jieguo_data(i,2)=xingzuo_data(i,2);     ...

  6. boost::safe_numerics模块实现数组索引值可以超出数组边界的测试程序

    boost::safe_numerics模块实现数组索引值可以超出数组边界的测试程序 实现功能 C++实现代码 实现功能 boost::safe_numerics模块实现数组索引值可以超出数组边界的测 ...

  7. php 数组大于1,位置 1 的索引超出数组范围(不能超过 1)。

    %清空运行环境 clc clear %速度更新参数 c1 = 1.49445; c2 = 1.49445; maxgen = 300; %最大迭代次数 sizepop = 20; %种群规模数 %个体 ...

  8. matlab出现索引超出数组元素的数目(0)怎么解决

    Matlab 出现索引超出数组元素的数目 (0) 通常表示你试图访问一个空数组或者超出数组索引的范围.以下是一些可能的解决方案: 检查你的代码,确保没有在程序中使用空数组. 检查数组的索引是否正确.例 ...

  9. matlab超出所有矩阵维度,matlab中索引超出矩阵维度

    公告: 为响应国家净网行动,部分内容已经删除,感谢读者理解. 话题:matlab中索引超出矩阵维度?回答:beta=4; % beta 是一个常量 beta(alpha,beta) % beta 不是 ...

最新文章

  1. Lesson 4.张量的线性代数运算
  2. html控制按钮里面的文字,有谁可以告诉我web网页制作中通过三个按钮控制页面上的一段文字放? 爱问知识人...
  3. 【Python3网络爬虫开发实战】1.3.3-pyquery的安装
  4. 子进程中获取父进程id_进程全家桶,看这一篇就够了 | 原力计划
  5. 吴恩达《机器学习》第十六章:推荐系统
  6. 【高并发高性能高可用之海量数据MySQL实战】-提纲目录-不断更新中...
  7. 草图大师SketchUp2020安装详细教程(官方中文版)
  8. 被V神点赞, 我是如何用五子棋打败以太坊排名最高的应用的? |人物志
  9. database2sharp mysql_Database2Sharp免费版
  10. 电脑硬盘图标换成自己喜欢的图标
  11. 高斯函数的傅里叶变换
  12. 系统部署在服务器,如何把系统部署在云服务器
  13. 20169220 网络攻防实践 第二周学习总结
  14. 手机/平板上如何进行网页过滤
  15. java中的finalize
  16. Android自动股票,腾讯股票自选股 Android 版上线 - YangJunwei
  17. RHEL6/7更新系统的CA
  18. TIOBE 2021 年度编程语言:Python
  19. 【优化布局】基于免疫算法求解充电站最优布局matlab代码
  20. Mybatis之关联关系映射

热门文章

  1. azg集团携手Bubs开展战略合作,为中国用户提供优质奶粉
  2. php sqlite linux,linux+apache+sqlite+php - 唐老鸭的日志 - 网易博客
  3. 简陋的spring cloud搭建并部署云服务器
  4. Vmware下Ubuntu18.04虚拟机右上角的网络图标消失连不上网络,找回方法。
  5. 尚学堂Oracle 课堂笔记(收藏)
  6. spring-bean对象创建销毁顺序depend-on 干预
  7. ElasticsearchTemplate 的API
  8. onKeyDown()方法详解
  9. 北京4条在建地铁将提前开通 10号线二期明年通
  10. 创建日志表和插日志信息的sp