前言
前面忘记说了,在学习算法之前呢,至少需要了解一门编程语言,其实是什么语言不重要,都可以的,我后面博客会一直使用Java,因为Java是我的主语言,目前尽量每天更新一章,可能到后面我自己也没学的可能就的一周更新一章了,希望不要烂尾吧,也请多多指教。
什么是数组
,在我们学习编程语言的时候,必然会学习一些存储数据的容器,例如Java的List、Map等等,也有最初的 int[] 数组,好吧这就是数组的了,数组是一片连续的存储空间,当然既然有连续,那肯定有不连续(链表),如图:
可以看到申请的内存空间都是连续的。
数组的特点:
1、内存空间是连续的
2、可随机访问
3、存储的元素,数据类型一致
用Java来定义的一个数组,如下
public static void main(String[] args) {
int[] nums={1,3}; //指定元素
int[] nums1=new int[2]; //指定长度
}
当然不同的语言可能方法不同,其实这些应该在初学编程的时候会讲
我写点不一样的吧
数组是如何实现随机访问的
如图,假设我们每个元素占1个空间,这是一个7个元素的内存空间
代码如下
public static void main(String[] args) {
char[] nums1=new char[7]; //指定长度
}
在c语言里面有这样一句话,数据名即首地址,也可以用到这里,我们已知首地址为1000,假设我们要访问第4个元素,那么第n个元素的内存地址的计算方式为 内存地址=首地址+(每个元素大小n) ; 第4个元素地址为 1000+(14) =1004 这就计算出来了。
当然我们这里是从第0个元素开始的,,正常情况下我们在编程的时候,数组的访问也是从0开始的。
数组的增删改查
这里聊一聊数组的增删改查
数组的新增
按照不同情况,时间复杂度也不一样,数组的每一次插入元素,为了保证顺序,都会将数组中的元素依次往后移,
假设我们要在第三个位置插入一个内容为F的元素
代码如下:
public class erf {
static int[] nums={1,2,3,4,5,0,0}; //0为空的空间
static int num=5; //数组中元素个数
public static void insert(int index,int k){
for(int i=num;i>index;i--){
nums[i]=nums[i-1];
}
nums[index]=k;
num++;
}
public static void main(String[] args) {
for (int i:nums) {
System.out.print(i+" ");
}
erf.insert(3,10);
System.out.println();
for (int i:nums) {
System.out.print(i+" ");
}
}
}
当然,如果不需要保证顺序,那也可以直接将待插入的元素位置的元素复制到数组最后,然后再更新带插入位置的值 如图
数组的删除
删除元素跟插入元素类似,如果我们要删除第k个位置的数据,为了内存的连续性,也需要搬移数据,不然中间就会出现空洞,内存就不连续了。
和插入类似,如果删除数组末尾的数据,则最好情况时间复杂度为O(1);如果删除开头的数据,则最坏情况时间复杂度为O(n);平均情况时间复杂度也为O(n)。
如图:
数组元素的查找
数组元素的查找分为按值查找和按下标查找,当然按下标查找肯定是最快的,我们上面说过,时间复杂度是O(n)。
而按值查找就需要遍历数组,然后一个一个的对比了,时间复杂度是O(n)
数组的优劣性
数组拥有非常高的随机访问能力,只要给出下标就可以很快找到对应的元素,有一种高效的查找元素方法,叫二分查找,后期我会写,就是利用了这个优势,
而数组的劣势体现再插入元素和删除元素方面,由于数组的连续性,插入删除元素都会导致元素大量的搬迁,影响效率。
总结
数组适合读操作多,写操作少的场景