返回

5 种经典排序算法 JS 实现 | 刷题打卡

前端

探索经典排序算法的 JavaScript 实现

排序算法是计算机科学领域的基石,广泛应用于处理数据、管理待办事项列表以及处理海量数据集。它们的基本原则涉及将元素排列成特定顺序(例如升序或降序)。在这篇文章中,我们将深入探究五种经典排序算法的 JavaScript 实现,帮助你掌握排序的精髓。

1. 冒泡排序

冒泡排序是一种简单但效率较低的算法,它通过反复比较相邻元素,将较大的元素逐渐“浮”到列表末尾。这种算法最适合处理小型数据集,但当数据量较大时会变得非常缓慢。

function bubbleSort(arr) {
  for (let i = 0; i < arr.length; i++) {
    for (let j = 0; j < arr.length - i - 1; j++) {
      if (arr[j] > arr[j + 1]) {
        // 交换元素
        let temp = arr[j];
        arr[j] = arr[j + 1];
        arr[j + 1] = temp;
      }
    }
  }

  return arr;
}

2. 插入排序

插入排序是一种比冒泡排序更有效且更快速的算法。它逐个插入元素到已经排序的部分,通过与相邻元素比较并进行相应移动来维持整体有序性。

function insertionSort(arr) {
  for (let i = 1; i < arr.length; i++) {
    let key = arr[i];
    let j = i - 1;

    // 将 key 插入到排序部分的正确位置
    while (j >= 0 && key < arr[j]) {
      arr[j + 1] = arr[j];
      j--;
    }

    arr[j + 1] = key;
  }

  return arr;
}

3. 选择排序

选择排序通过反复寻找并交换列表中最小(或最大)元素到当前未排序部分的开头,逐步构建有序序列。它比插入排序效率稍低。

function selectionSort(arr) {
  for (let i = 0; i < arr.length; i++) {
    let minIndex = i;

    // 寻找未排序部分中的最小元素
    for (let j = i + 1; j < arr.length; j++) {
      if (arr[j] < arr[minIndex]) {
        minIndex = j;
      }
    }

    // 交换最小元素和未排序部分的第一个元素
    let temp = arr[i];
    arr[i] = arr[minIndex];
    arr[minIndex] = temp;
  }

  return arr;
}

4. 归并排序

归并排序是一种分治算法,它将列表分成较小的部分,分别对其进行排序,然后合并排序后的部分。这种算法具有稳定的时间复杂度 O(n log n),使其非常适合处理大型数据集。

function mergeSort(arr) {
  if (arr.length <= 1) {
    return arr;
  }

  // 分解数组
  const mid = Math.floor(arr.length / 2);
  const left = mergeSort(arr.slice(0, mid));
  const right = mergeSort(arr.slice(mid));

  // 合并已排序的部分
  return merge(left, right);
}

function merge(left, right) {
  const merged = [];

  while (left.length && right.length) {
    if (left[0] < right[0]) {
      merged.push(left.shift());
    } else {
      merged.push(right.shift());
    }
  }

  return merged.concat(left, right);
}

5. 快速排序

快速排序也是一种分治算法,它通过选择一个枢纽元素将列表分成两个子列表,其中一个包含小于枢纽的元素,另一个包含大于枢纽的元素。然后递归地对每个子列表进行排序。平均情况下,快速排序的时间复杂度为 O(n log n),但在最坏情况下可能退化为 O(n^2)。

function quickSort(arr) {
  if (arr.length <= 1) {
    return arr;
  }

  // 选择枢纽元素
  const pivot = arr[Math.floor(arr.length / 2)];
  const left = [];
  const right = [];

  // 分区数组
  for (let i = 0; i < arr.length; i++) {
    if (arr[i] < pivot) {
      left.push(arr[i]);
    } else if (arr[i] > pivot) {
      right.push(arr[i]);
    }
  }

  // 递归排序子列表
  return quickSort(left).concat(pivot, quickSort(right));
}

常见问题解答

1. 不同的排序算法有什么优缺点?

每种排序算法都有其优缺点。冒泡排序和选择排序简单易懂,但效率较低。插入排序在部分排序的数据集上表现良好,而归并排序和快速排序效率更高,但实现起来更复杂。

2. 哪种排序算法最适合处理大型数据集?

归并排序和快速排序最适合处理大型数据集,因为它们的时间复杂度与数据集大小成比例增长。

3. 排序算法在现实世界中有什么应用?

排序算法广泛应用于各种领域,包括:
- 整理数据表和电子表格
- 优化搜索算法
- 创建索引
- 处理文本和自然语言

4. 如何选择最合适的排序算法?

算法选择取决于数据大小、数据集是否部分排序以及对效率和复杂性的要求。

5. 排序算法的未来发展方向是什么?

排序算法仍在不断发展,随着计算机硬件和算法设计技术的进步,新的算法不断被提出,以提高效率和处理更大更复杂的数据集的能力。