以下是常见数据结构的详细解释及Java示例代码,结合了知识库中的核心概念和实现细节:
1. 数组(Array)
特点:
- 线性结构,内存连续,固定大小。
- 优点:快速随机访问(O(1))。
- 缺点:插入/删除效率低(O(n))。
Java示例:
public class ArrayExample {
public static void main(String[] args) {
// 定义数组
int[] arr = {1, 2, 3, 4, 5};
// 访问元素
System.out.println("元素 2 的值:" + arr[1]); // 输出 2
// 遍历数组
for (int num : arr) {
System.out.print(num + " "); // 输出 1 2 3 4 5
}
}
}
2. 链表(Linked List)
特点:
- 线性结构,动态大小,非连续内存。
- 优点:插入/删除高效(O(1)时间,但需找到位置)。
- 缺点:无法随机访问,需遍历查找。
Java示例(自定义单链表):
class ListNode {
int val;
ListNode next;
ListNode(int val) { this.val = val; }
}
public class LinkedListExample {
public static void main(String[] args) {
// 创建链表:1 -> 2 -> 3
ListNode head = new ListNode(1);
head.next = new ListNode(2);
head.next.next = new ListNode(3);
// 遍历链表
ListNode current = head;
while (current != null) {
System.out.print(current.val + " "); // 输出 1 2 3
current = current.next;
}
}
}
3. 栈(Stack)
特点:
- 线性结构,后进先出(LIFO)。
- Java实现:使用
Deque接口(推荐)或Stack类。
Java示例:
import java.util.Deque;
import java.util.ArrayDeque;
public class StackExample {
public static void main(String[] args) {
Deque<Integer> stack = new ArrayDeque<>();
stack.push(1); // 入栈
stack.push(2);
stack.push(3);
System.out.println("栈顶元素:" + stack.peek()); // 输出 3
while (!stack.isEmpty()) {
System.out.print(stack.pop() + " "); // 输出 3 2 1(出栈顺序)
}
}
}
4. 队列(Queue)
特点:
- 线性结构,先进先出(FIFO)。
- Java实现:使用
Queue接口(如LinkedList或ArrayDeque)。
Java示例:
import java.util.Queue;
import java.util.LinkedList;
public class QueueExample {
public static void main(String[] args) {
Queue<Integer> queue = new LinkedList<>();
queue.offer(1); // 入队
queue.offer(2);
queue.offer(3);
System.out.println("队列头部元素:" + queue.peek()); // 输出 1
while (!queue.isEmpty()) {
System.out.print(queue.poll() + " "); // 输出 1 2 3(出队顺序)
}
}
}
5. 哈希表(Hash Table)
特点:
- 非线性结构,通过键值对(Key-Value)存储。
- 优点:平均O(1)的增删改查。
- Java实现:
HashMap(基于数组+链表/红黑树)。
Java示例:
import java.util.HashMap;
public class HashMapExample {
public static void main(String[] args) {
HashMap<String, Integer> map = new HashMap<>();
map.put("Alice", 25); // 添加键值对
map.put("Bob", 30);
System.out.println("Alice的年龄:" + map.get("Alice")); // 输出 25
map.remove("Bob"); // 删除键
System.out.println("哈希表大小:" + map.size()); // 输出 1
}
}
6. 二叉树(Binary Tree)
特点:
- 非线性结构,每个节点最多有两个子节点(左、右)。
- Java实现:自定义节点类。
Java示例(简单二叉树结构):
class TreeNode {
int val;
TreeNode left, right;
TreeNode(int val) { this.val = val; }
}
public class BinaryTreeExample {
public static void main(String[] args) {
// 创建二叉树:
// 1
// / \
// 2 3
TreeNode root = new TreeNode(1);
root.left = new TreeNode(2);
root.right = new TreeNode(3);
// 遍历根节点的左右子节点
System.out.println("根节点:" + root.val);
System.out.println("左子节点:" + root.left.val);
System.out.println("右子节点:" + root.right.val);
}
}
7. 堆(Heap)
特点:
- 完全二叉树结构,满足堆性质(最大堆/最小堆)。
- Java实现:
PriorityQueue(默认最小堆)。
Java示例:
import java.util.PriorityQueue;
public class HeapExample {
public static void main(String[] args) {
// 最小堆示例
PriorityQueue<Integer> minHeap = new PriorityQueue<>();
minHeap.add(3);
minHeap.add(1);
minHeap.add(2);
System.out.println("堆顶元素:" + minHeap.peek()); // 输出 1
while (!minHeap.isEmpty()) {
System.out.print(minHeap.poll() + " "); // 输出 1 2 3(按顺序弹出)
}
}
}
8. 图(Graph)
特点:
- 非线性结构,由节点(顶点)和边组成。
- Java实现:邻接表(常用)。
Java示例(无向图邻接表):
import java.util.*;
class Graph {
private int vertices;
private LinkedList<Integer>[] adjList;
public Graph(int vertices) {
this.vertices = vertices;
adjList = new LinkedList[vertices];
for (int i = 0; i < vertices; i++) {
adjList[i] = new LinkedList<>();
}
}
public void addEdge(int src, int dest) {
adjList[src].add(dest);
adjList[dest].add(src); // 无向图需双向添加
}
public void printGraph() {
for (int v = 0; v < vertices; v++) {
System.out.print("顶点 " + v + " 的邻接点:");
for (int neighbor : adjList[v]) {
System.out.print(neighbor + " ");
}
System.out.println();
}
}
}
public class GraphExample {
public static void main(String[] args) {
Graph graph = new Graph(4);
graph.addEdge(0, 1);
graph.addEdge(0, 2);
graph.addEdge(1, 3);
graph.addEdge(2, 3);
graph.printGraph();
// 输出:
// 顶点 0 的邻接点:1 2
// 顶点 1 的邻接点:0 3
// 顶点 2 的邻接点:0 3
// 顶点 3 的邻接点:1 2
}
}
总结对比
| 结构 | 特点 | Java实现类 | 适用场景 |
|---|---|---|---|
| 数组 | 固定大小,随机访问快 | int[], ArrayList | 频繁访问已知索引的场景 |
| 链表 | 动态大小,插入/删除高效 | LinkedList | 频繁插入/删除的场景 |
| 栈 | 后进先出(LIFO) | Deque(推荐) | 递归、表达式求值 |
| 队列 | 先进先出(FIFO) | LinkedList, ArrayDeque | 消息队列、任务调度 |
| 哈希表 | 快速查找/插入/删除 | HashMap, TreeMap | 唯一键值对存储(如缓存) |
| 二叉树 | 层次化结构,高效查找 | 自定义节点类 | 文件系统、搜索算法(如BST) |
| 堆 | 优先级队列 | PriorityQueue | 调度任务(如Dijkstra算法) |
| 图 | 复杂关系建模 | 邻接表/邻接矩阵 | 社交网络、路径规划(如Dijkstra) |
选择建议
- 随机访问 → 数组/ArrayList。
- 频繁插入/删除 → 链表/LinkedList。
- 键值对快速查找 → 哈希表(HashMap)。
- 优先级操作 → 堆(PriorityQueue)。
- 复杂关系建模 → 图(邻接表)。
通过结合场景需求和数据结构特性,可以高效选择合适的结构!