我估计很多程序员都有个疑惑:为什么很多编程语言的数组索引都是从0开始的?,接下来我们就来聊聊关于数组索引值为非正值?以下内容大家不妨参考一二希望能帮到您!

数组索引值为非正值(你知道数组索引从零开始的原因吗)

数组索引值为非正值

我估计很多程序员都有个疑惑:为什么很多编程语言的数组索引都是从0开始的?

数组索引从零开始起源于 C 甚至汇编程序。使用 C,指针基本上是这样工作的:

为了说明,假设int a[3]在 1012,地址是:

因此,对于从零开始的索引,地址数学很简单:

元素地址 = 数组地址 索引 * sizeof(type)

事实上,C 中的表达式都是等价的:

使用基于 1 的索引,我们必须编写i < n 1,这样多执行一条指令,稍微复杂一些。

因此,由于历史原因,java、JavaScript援用索引从0开始的这个约定

荷兰的Dijkstra教授解释了为什么这种约定效果最好。归根结底,我们希望将整数序列表示为包含起始端的半开区间。

为了表示三个点的自然数 2、3、...、12 的子序列,我们可以使用四种约定a) 2 ≤ i < 13b) 1 < i ≤ 12c) 2 ≤ i ≤ 12d ) 1 < i < 13

套用 Dijkstra:

  • (a) 和 (b) 的优点是减去边界可以得到长度,这很方便,因为您不需要记住加或减 1。
  • (a) 和 (c) 的优点是从零开始的序列不需要负下限——负数不再是自然数。
  • (a) 和 (d) 的优点是,如果您创建一个从零开始的区间并将其缩小到零长度,则上限不需要负数。

由于上述原因,我们希望将所有区间写为 (a)。

一旦您接受 (a) 是指定间隔的正确方法,将长度为 N 的数组索引为 [0, N) 比 [1, N 1) 好得多。

支持使用 (a) 表示音程的两个附加说明。

上面的第一点很重要,因为半开区间很好地分解为其他半开区间。这使得实现像合并排序这样的分而治之算法显着不易出错。

例如:

  • [4, 14) 可以分解为大小相等的区间 [4, 9) 和 [9, 14),中间索引计算为 $9 = \frac{4 14}{2}$。
  • [4, 13],分解为 [4, 8] 和 [9, 13],其中一个序列的结尾为 $8 = \frac{4 13 1}{2} - 1$,而开头下一个序列为 $9 = \frac{4 13 1}{2}$。很容易忘记在某处加或减 1。

用 (b) 指定间隔也有点不协调,因为在编写循环时跳过第一个元素感觉不自然。

Dijkstra 的解释很好地证明了在 编程中使用通用方案的合理性。

,