首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> Java 程式設計 >> Java 程式設計入門

Java 陣列核心知識體系:定義、初始化、操作 API 與經典演算法實戰

     編輯:Java 程式設計入門

前言

陣列是 Java 最基礎、最高效的容器,也是集合框架、序列化、JNI 互操作的底層支撐。本文系統梳理**記憶體模型、三種初始化模式、核心操作 API、經典演算法模板、陣列 vs 集合選型**五大板塊,並附贈生產級工具類與避坑清單。

一、記憶體模型與核心特性

特性說明影響
堆上分配new int[10] 在 Heap 分配連續記憶體受 GC 管理、可觸發 Minor GC、大陣列直接進 Old Gen
固定長度創建後長度不可變擴容需手動 Arrays.copyOf、System.arraycopy
類型安全編譯期強制檢查元素類型避免 ClassCastException、JIT 優化友好
邊界檢查每次存取執行 ArrayIndexOutOfBoundsException 檢查安全但有微小開銷 (JIT 會消除熱點迴圈檢查)
預設值引用型 null、基本型 0/false/0.0無需手動初始化、但語義上建議顯式賦值
length 欄位final、非方法、O(1) 存取效能優於 Collection.size()

二、三種初始化模式深度解析

1. 靜態初始化 (編譯期常量)


// 編譯期確定內容,字節碼內嵌常量池
int[] primes = {2, 3, 5, 7, 11};
String[] weekDays = {"Mon", "Tue", "Wed", "Thu", "Fri", "Sat", "Sun"};
Color[] palette = {Color.RED, new Color(0x00FF00), Color.BLUE};
  • **語法糖**:編譯器自動生成 new int[]{...} + arraycopy。
  • **限制**:只能在宣告語句中使用,不能分離宣告與賦值。

2. 動態初始化 (運行期分配)


// 1. 宣告引用
int[] scores;

// 2. 分配記憶體 (預設值 0)
scores = new int[100];

// 3. 迴圈賦值 (業務邏輯)
for (int i = 0; i < scores.length; i++) {
    scores[i] = ThreadLocalRandom.current().nextInt(101);
}

3. 預設初始化 (隱式)


// 僅分配記憶體,依賴 JVM 零填充
int[] arr = new int[10]; // 全 0
Object[] objs = new Object[10]; // 全 null

⚠️ **陷阱**:int[] a = new int[3]; a[0] = 1; a[1] = 2; // a[2] 隱式為 0 —— 若業務 0 有特殊含義 (如 ID=0 非法),**必須顯式初始化或用 -1 哨兵值**。

三、多維陣列與鋸齒陣列


// 規則二維陣列 (矩形)
int[][] matrix = new int[3][4]; // 3 行 4 列,連續記憶體塊

// 鋸齒陣列 (每行長度不同) —— 節省記憶體、對應不規則數據
int[][] jagged = new int[3][];
jagged[0] = new int[5];
jagged[1] = new int[3];
jagged[2] = new int[2];
// 記憶體分佈:3 個獨立一維陣列 + 1 個引用陣列

四、核心操作 API (java.util.Arrays)

操作API複雜度備註
複製Arrays.copyOf(arr, newLen)O(n)擴容/縮容首選,內部 System.arraycopy
區間複製Arrays.copyOfRange(arr, from, to)O(to-from)左閉右開 [from, to)
排序 (基本型)Arrays.sort(arr)O(n log n)Dual-Pivot QuickSort (JDK 7+)
排序 (物件)Arrays.sort(arr, Comparator)O(n log n)TimSort (穩定、適應性強)
二分搜尋Arrays.binarySearch(arr, key)O(log n)**前提:已排序**
填充Arrays.fill(arr, val)O(n)重置陣列、哨兵值初始化
比較Arrays.equals(arr1, arr2)O(n)深度比較用 Arrays.deepEquals
轉字串Arrays.toString(arr)O(n)除錯神器、避免 [I@15db9742
並行排序Arrays.parallelSort(arr) (JDK 8+)O(n log n) / P大陣列 (>8192) 效能顯著提升
流式操作Arrays.stream(arr)-函數式風格、配合 filter/map/reduce

五、經典演算法模板 (面試/業務通用)

1. 陣列初始化 1..N


// 思路 1: 下標映射
int[] a = new int[100];
for (int i = 0; i < a.length; i++) a[i] = i + 1;

// 思路 2: 值驅動 (適用於非 0 起始)
int[] b = new int[100];
for (int v = 1; v <= 100; v++) b[v - 1] = v;

2. 費波納契數列 (前 N 項)


int[] fib = new int[20];
fib[0] = 1; fib[1] = 1;
for (int i = 2; i < fib.length; i++) {
    fib[i] = fib[i-1] + fib[i-2];
}

3. 原地反轉 (O(1) 空間)


void reverse(int[] a) {
    for (int i = 0, j = a.length - 1; i < j; i++, j--) {
        int tmp = a[i]; a[i] = a[j]; a[j] = tmp;
    }
}

4. 移除指定值 (LeetCode 27 風格)


// 返回新長度,前段為有效元素
int removeElement(int[] nums, int val) {
    int slow = 0;
    for (int fast = 0; fast < nums.length; fast++) {
        if (nums[fast] != val) nums[slow++] = nums[fast];
    }
    return slow;
}

5. 合併兩個有序陣列 (LeetCode 88)


// nums1 尾部有足夠空間,從後向前合併
void merge(int[] nums1, int m, int[] nums2, int n) {
    int i = m - 1, j = n - 1, k = m + n - 1;
    while (j >= 0) {
        nums1[k--] = (i >= 0 && nums1[i] > nums2[j]) ? nums1[i--] : nums2[j--];
    }
}

六、陣列 vs 集合選型指南

場景推薦理由
長度固定、高頻隨機存取、基本型陣列記憶體緊湊、無裝箱、JIT 向量化、最快
長度動態、頻繁增刪、業務模型豐富ArrayList封裝擴容、泛型安全、豐富 API
首尾增刪、佇列/棧語義ArrayDequeO(1) 兩端操作、無容量上限
高併發、無鎖、快照讀CopyOnWriteArrayList讀寫分離、迭代器不拋 CME
基本型大量儲存、記憶體敏感陣列 / 基本型集合庫 (Eclipse Collections, FastUtil)避免裝箱開銷、節省 50%+ 記憶體

七、避坑清單

  1. 陣列變量賦值只是引用複製:int[] b = a; b[0]=99; // a[0] 也變成 99 —— 需獨立副本請用 Arrays.copyOf。
  2. Arrays.asList 返回固定大小列表:list.add() 拋 UnsupportedOperationException —— 需 new ArrayList<>(Arrays.asList(...))。
  3. 基本型陣列無法用泛型:List ✅,List ❌ —— 用 IntStream 或專用庫。
  4. 大陣列直接進 Old Gen:new byte[10_000_000] 可能觸發 Full GC —— 預分配、分批、堆外記憶體。
  5. 多維陣列非連續:int[][] m = new int[1000][1000] 實際 1001 個物件 —— 扁平化 int[] flat = new int[1_000_000] 更緊湊。

💡 核心心法:能用基本型陣列就別用包裝類集合;能用 Arrays 標準庫就別手寫迴圈;動態長度首選 ArrayList,固定長度首選陣列;大陣列注意 GC 壓力,考慮堆外或分塊。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved