阵列(数据结构)
数组的属性
最简单的数组实现仅存储其第一索引的内存地址。某些语言还存储数组的大小以防止缓冲区溢出错误。通过索引来执行给定索引处的项目的插入和检索 ,乘以项目大小 在字节数中,并将其添加到基本存储器地址 。
对于零基编号,内存地址 索引是给出的
考虑C中的以下代码片段:
1 2 3 4 5 6UINT32_T.质数[5.];质数[0.]=2;质数[1]=3.;质数[2]=5.;质数[3.]=7.;质数[4.]=11.;
第1行声明了一个长度5的数组,其中包含32位无符号整数。32位是4个字节,所以我们的物品大小 是4.这意味着我们的数组是 总体大小的字节。第一个索引被分配了任意内存地址;为我们的例子,让我们说 。整个数组使用内存地址 通过 。
第2-6行每个每个计算给定索引的内存地址,并将值写为4字节无符号整数。例如,在线5中,索引3的存储器地址是 因此,值7被写为在地址开始的4字节无符号整数 。
将异构性大小存储在C中的数组中,指针对于这些项目,而不是物品本身,必须明确地存储。这是阵列如何以Java和Python等更高级别的语言工作。存储对实际项目的引用而不是直接存储原始项目。这一切都含蓄地,因为Java和Python没有指针类型。这样的结果是,依次遍历阵列可能实际意味着访问非连续的存储器部分。而不是在内存的连续部分中存在的所有值,而是将值存储在存储器中的任意位置,其可以彼此远离。数据的位置和CPU有效缓存的能力丢失。
阵列具有固定大小,在创建时声明。更复杂的数据结构,允许在创建之后调整数组的大小动态阵列。
时间复杂性
阵列是最快的数据结构之一,因为索引查找过程只是一个整数乘法操作,然后是整数加法操作 - 在现代CPU上的非常快速的操作。以下是所需基本功能的时间复杂性阵列(ADT)。
手术 | 复杂 |
得到 | |
放 |
空间复杂性
阵列相对于元素数量占用线性空间 他们抱着。它们还具有内存中没有空间浪费的好处(因为它初始化了一定尺寸):
二维阵列
二维阵列也存储在连续存储器中。对于基于零的编号语言,给定索引的项目的内存地址 和 在一系列项目大小 字节, 行, 列和基本存储器地址 是(谁)给的
考虑C中的以下代码片段:
1 2 3 4 5 6 7UINT32_T.转变[3.] [2];转变[0.] [0.]=37.;转变[0.] [1]=0.;转变[1] [0.]=0.;转变[1] [1]=39.;转变[2] [0.]=1;转变[2] [1]=4.;
第1行声明了一系列二维数组 行和 包含32位无符号整数的列。32位是4个字节,所以我们的物品大小 是4.这意味着我们的数组是 总体大小的字节。第一个索引被分配了任意内存地址;为我们的例子让我们说 。整个数组使用内存地址 通过 。
第2-7行每个计算给定索引的内存地址,并将值写为4字节无符号整数。例如,在第7行,索引的内存地址 那 是 因此,值4被写为以地址开始的4字节无符号整数 。
该技术可以广泛地存储 - 连续内存中的阵列。
锯齿状阵列
二维阵列覆盖多于是定义始终矩形。通常情况下,这并不完全适应手头的问题,最终会浪费空间。这可以通过使用一维阵列来避免这一点,该阵列存储对异构长度的其他一维阵列的引用。这略微慢,因为它增加了一个间接级别,但通常倍数的时间使得保存的内存使其值得。java和python等更高级别语言仅允许为多维数组进行锯齿状阵列。