主要是對數組所有的東西進行總結,整理
適合小白~
目錄
1.什么是數組
1.1數組定義
1.2數組創建
1)靜態創建
2)動態創建
?1.3數組遍歷
1)for和while遍歷
2)foreach遍歷
2.數組越界問題及解決
2.1數組越界問題
2.2越界問題解決----數組拷貝擴容
1)防止發生:
2)發生后解決:
3)采用List list = new ArrayList<>();
3.數組算法
3.1插入算法
1)尾插法
2)指定位置插入法
2.刪除
1)刪除第一個符合條件的數據
2)刪除所有符合條件的數據
3)使用快慢指針刪除元素
3.查找算法
1)二分查找法
1.什么是數組
1.1數組定義
數組是一種用于存儲固定大小的同類型元素的集合,是一種數據結構。
int[] arr = {1,2,3,4,5,6,7,8,9,10};char[] chars = {'a','b','c','d','e','f','g','h','i','j'};String[] strings = {"hello","world","java","python","c++"};double[] doubles = {1.1,2.2,3.3,4.4,5.5,6.6,7.7,8.8,9.9,10.10};
1.2數組創建
有兩種方式。[兩者相比后者靈活性更高,區別不大,針對需求選擇格式使用]
1)靜態創建
在創建數組時就明確地指定數組中的元素,數組的長度由指定的元素個數決定。
// 基本數據類型數組
int[] staticArray1 = {1, 2, 3, 4, 5};
// 對象數組
String[] staticArray2 = {"apple", "banana", "cherry"};
2)動態創建
在創建數組時只指定數組的長度,而不具體給出數組元素的初始值。后續可以再對數組元素進行賦值操作。
// 基本數據類型數組
int[] dynamicArray1 = new int[5];List<Integer> list = new ArrayList<>();
?1.3數組遍歷
java中數組有兩種常見的遍歷方式
1)for和while遍歷
2)foreach遍歷
這種方式不能修改數組值和單獨訪問下標索引。形式為for( int name?: names)表示對數組names中的每個元素都復制給name然后執行
int[] arr = {1,2,3,4,5,6,7,8,9,10};
// for遍歷for (int i = 0; i < arr.length; i++) {System.out.println(arr[i]);}
// while遍歷int i = 0;while (i< arr.length){System.out.println(arr[i]);}
// foreach遍歷for (int i : arr) {System.out.println(i);}
2.數組越界問題及解決
2.1數組越界問題
數組越界:訪問的索引值超過了數組的最大長度-1[因為數組下標從0開始]。或者是添加元素超過了數組最大長度-1、刪除數組中沒有的元素
越界異常提示實例如下:
int[] arr = {1,2,3,4,5,6,7,8,9,10};System.out.println(arr[10]);
提示為:
Exception in thread "main" java.lang.ArrayIndexOutOfBoundsException: Index 10 out of bounds for length 10
?? ?at com.weimeng.test.array.main(array.java:25)
2.2越界問題解決----數組拷貝擴容
發生越界后有以下解決方法:
1)防止發生:
仔細檢查索引計算:在編寫代碼時,要確保索引的計算不會超出數組的有效范圍。
進行邊界檢查:在訪問數組元素之前,先檢查索引是否在有效范圍內。可以編寫一個if輔助方法來進行邊界檢查,避免越界訪問。
2)發生后解決:
數組擴容:就是創建新數組再拷貝原數組元素,新數組的長度更長。先創建新數組,再將原數組元素復制過來,最后替換引用。如下:
int[] arr = {1,2,3,4,5,6,7,8,9,10};
// 數組擴容
//先創建新數組,再將原數組元素復制過來,最后替換引用int len=arr.length;double factor=1.5;//擴大因子int[] brr=new int[(int) (len*factor)];//新數組for(int i=0;i<len;i++){brr[i]=arr[i];}arr=brr;System.out.println(arr[10]);
3)采用List<Integer> list = new ArrayList<>();
這種方法可以防止添加元素越界,訪問越界和刪除越界可以再結合1)方式。
3.數組算法
3.1插入算法
數組的插入算法是指在數組的特定位置插入一個新元素的操作。由于數組的特性(元素在內存中連續存儲,長度固定),插入元素可能需要移動其他元素來騰出空間。
1)尾插法
尾插法過程:判斷數組滿沒滿,沒滿就直接放入數組最后元素的下一個位置;滿了就進行擴容再插入。整個過程通過size控制,代碼如下:
public class Array1 {int size=0;int len=10;double factor=1.5;//擴大因子int arr[]=new int[len];// 目標:實現尾插法public static void main(String[] args) {Array1 list=new Array1();list.add(1);list.add(2);list.add(3);System.out.println(list.toString());}public void add(int data){if(size==len){len=(int)(len*factor);int[] brr=new int[len];for(int i=0;i<size;i++){brr[i]=arr[i];}arr=brr;}arr[size]=data;size++;}public String toString(){String str="[";for(int i=0;i<size;i++){str+=arr[i];if(i!=size-1){str+=",";}}str+="]";return str;}
}
2)指定位置插入法
算法原理:先判斷插入位置是否合理,保證代碼合法性;再判斷數組是否滿;插入時反向循環,先將size++,然后arr[i]=size[i-1]進行循環,如下圖所示:
// 指定位置插入public void addAtIndex(int index,int data){//保證數組訪問安全if(index<0||index>size){System.out.println("超出范圍");return;}//擴容if(size==len){len=(int)(len*factor);int[] brr=new int[len];for(int i=0;i<size;i++){brr[i]=arr[i];}arr=brr;}size++;for(int i=size;i>index;i--){arr[i]=arr[i-1];}arr[index]=data;}public String toString(){String str="[";for(int i=0;i<size;i++){str+=arr[i];if(i!=size-1){str+=",";}}str+="]";return str;}
2.刪除
1)刪除第一個符合條件的數據
原理:從前向后遍歷,找刪除的數據。找不到直接輸出“不存在該元素”;找到則記錄該位置,通過循環從該位置開始,arr[i]=arr[i+1]覆蓋掉,size--,輸出“刪除完成"
public void remove(int data) {for (int i = 0; i < size; i++) {if (arr[i] == data) {// 移動元素覆蓋要刪除的元素for (int j = i; j < size - 1; j++) {arr[j] = arr[j + 1];}// 最后一個有效位置置為默認值arr[size - 1] = 0;size--;System.out.println("刪除成功");return;}}System.out.println("不存在該元素");}
2)刪除所有符合條件的數據
即通過循環遍歷元素,遇到arr[i]==data就進行刪除,如下:
public void delete(int data) {for(int i=0;i<size;i++){if(arr[i]==data){for(int j=i+1;j<size;j++){arr[j-1]=arr[j];}size--;i--;}}}
3)使用快慢指針刪除元素
- 慢指針(
slow
):用于記錄刪除特定元素后數組的有效長度,它指向的位置是下一個非data元素應該存放的位置。 - 快指針(
fast
):用于遍歷數組中的每一個元素。
具體步驟:
1.初始化兩個指針:slow
?和?fast
,都指向arr的起始位置(索引為 0)。
2.使用?fast
?指針遍歷數組:如果?fast
?指針指向的元素不等于data,則將該元素賦值給?slow
?指針指向的位置,然后?slow
?指針向后移動一位。如果?fast
?指針指向的元素等于data,則跳過該元素,slow
?指針保持不動。
重復步驟 2,直到?fast
?指針遍歷完整個數組。最終?slow
?指針的值就是刪除特定元素后數組的新長度。
代碼:
// 使用快慢指針刪除元素public void delete2(int data){int slow=0;int fast=0;while(fast<size){if(arr[fast]!=data){arr[slow]=arr[fast];slow++;}fast++;}size=slow;}
3.查找算法
1)二分查找法
二分查找適合有序數組,它的核心思想是不斷將查找區間縮小一半,以此減少查找范圍,從而快速定位目標元素。
算法內容:
1.先設置左右邊界,左邊界?left
?初始化為數組的第一個元素的索引(通常為 0),右邊界?right
?初始化為數組最后一個元素的索引(即數組長度減 1)。
2.再計算當前查找區間的中間元素的索引?mid
,計算公式為?mid = left + (right - left) / 2
。
3.比較中間元素跟目標元素:若中間元素等于目標元素,表明找到了目標元素,返回中間元素的索引。若中間元素大于目標元素,說明目標元素在左半部分區間,更新右邊界?right = mid - 1
。若中間元素小于目標元素,說明目標元素在右半部分區間,更新左邊界?left = mid + 1
。
4.重復2、3步,持續縮小查找區間,直到左邊界大于右邊界,此時表示目標元素不存在于數組中,返回 -1。
代碼:
public int binarySearch(int target) {int left = 0;int right = arr.length - 1;while (left <= right) {int mid = (right + left) / 2;if (arr[mid] == target) {return mid;} else if (arr[mid] < target) {left = mid + 1;} else {right = mid - 1;}}return-1;}