golang 归并排序,快速排序,堆排序的实现

Golang 实现归并排序,快速排序和堆排序

简介

排序算法的实现是大多数程序员必备的技能之一。在这个过程中,我们考虑三种经典的排序算法之一:归并排序,快速排序和堆排序。我们在学习它们的同时,也在学习使用 Golang 写出高效的排序算法。

归并排序

算法原理

归并排序是基于归并操作的一种排序算法,该算法的核心思想是将一个数组分成两个较小的数组,然后递归地将它们排序,最后再将它们合并来完成排序。它是一个稳定的算法,时间复杂度为 O(nlogn),空间复杂度也为 O(nlogn)。

实现步骤

  1. 将数组划分为两个更小的数组,其中一个包含前半部分,另一个包含后半部分。
  2. 递归地对这两个数组进行排序,直到只有一个元素。
  3. 排序时需要合并两个数组,合并时需要遍历两个数组,将较小的元素移动到新的数组中。
  4. 最后返回合并之后的结果。

代码示例

下面是归并排序算法的 Golang 实现代码:

func MergeSort(arr []int) []int {
    if len(arr) <= 1 {
        return arr
    }
    mid := len(arr) / 2
    left := MergeSort(arr[:mid])
    right := MergeSort(arr[mid:])
    return merge(left, right)
}

func merge(left, right []int) []int {
    res := []int{}
    i, j := 0, 0
    for i < len(left) && j < len(right) {
        if left[i] <= right[j] {
            res = append(res, left[i])
            i++
        } else {
            res = append(res, right[j])
            j++
        }
    }
    res = append(res, left[i:]...)
    res = append(res, right[j:]...)
    return res
}

以上代码中,MergeSort 和 merge 都是递归函数,merge 函数合并两个数组并返回一个新的数组。MergeSort 函数将原始数组拆分成两个数组并递归,最后返回合并后的结果。

快速排序

算法原理

快速排序是一种基于比较的排序算法,它使用分治法来将待排序的元素划分为较小和较大的子集,然后使用递归快速排序子集,直到子集为空或只包含一个元素。它是一个原地排序算法,平均时间复杂度为 O(nlogn),最坏情况为 O(n^2),空间复杂度为 O(1)。

实现步骤

  1. 选择数组中的一个基准元素。
  2. 遍历数组,将小于基准元素的放在左侧,大于等于基准元素的放在右侧。
  3. 对左右两侧的子数组进行递归,重复以上步骤直到子数组不能再分割。
  4. 最后将左侧、基准元素、右侧三部分合并到一起。

代码示例

以下是快速排序算法的 Golang 实现代码:

func QuickSort(arr []int, left, right int) {
    if left < right {
        mid := partition(arr, left, right)
        QuickSort(arr, left, mid-1)
        QuickSort(arr, mid+1, right)
    }
}

func partition(arr []int, left, right int) int {
    pivot := arr[right]
    i := left - 1
    for j := left; j < right; j++ {
        if arr[j] <= pivot {
            i++
            arr[i], arr[j] = arr[j], arr[i]
        }
    }
    arr[i+1], arr[right] = arr[right], arr[i+1]
    return i + 1
}

以上代码中,QuickSort 函数是递归函数,它定义了一个基准元素 pivot 和两个指针 left 和 right。QuickSort 函数随时分割子数组,从而实现快速排序。partition 函数是将数组分隔成较小值的子数组和较大值的子数组的关键函数。

堆排序

算法原理

堆排序是一种原地的排序,它是一种选择排序算法,它首先构建一个二叉树,并将其转换为堆,然后将所有的元素从堆中提取和删除,直到堆为空为止。它的时间复杂度为 O(nlogn),空间复杂度为 O(1)。

实现步骤

  1. 将数组构建成一个大根堆或小根堆。
  2. 循环地从堆顶选出最大或最小元素,并将其放在新数组的末尾。
  3. 调整堆结构,重新构建堆。
  4. 重复步骤 2 和 3 直到堆为空。

代码示例

以下是堆排序的 Golang 实现代码:

func HeapSort(arr []int) []int {
    length := len(arr)
    for i := length/2 - 1; i >= 0; i-- {
        heapify(arr, length, i)
    }
    for i := length - 1; i >= 0; i-- {
        arr[0], arr[i] = arr[i], arr[0]
        heapify(arr, i, 0)
    }
    return arr
}

func heapify(arr []int, length, p int) {
    left, right := p*2+1, p*2+2
    largest := p
    if left < length && arr[left] > arr[largest] {
        largest = left
    }
    if right < length && arr[right] > arr[largest] {
        largest = right
    }
    if largest != p {
        arr[p], arr[largest] = arr[largest], arr[p]
        heapify(arr, length, largest)
    }
}

以上代码中,HeapSort 函数首先构建一个最大堆,然后反复从堆的根节点提取最大元素,并重构最大堆。heapify 函数维护堆的性质,并保证父节点总是大于等于子节点的值。

结束语

以上就是归并排序、快速排序和堆排序算法的实现。这些算法都是经典的排序算法,也是每个程序员必须掌握的算法之一。在实际生产过程中,可以根据实际情况,选择不同的算法进行排序。

本站文章如无特殊说明,均为本站原创,如若转载,请注明出处:golang 归并排序,快速排序,堆排序的实现 - Python技术站

(0)
上一篇 2023年5月19日
下一篇 2023年5月19日

相关文章

  • JS前端面试必备——基本排序算法原理与实现方法详解【插入/选择/归并/冒泡/快速排序】

    JS前端面试必备——基本排序算法原理与实现方法详解 在前端面试中,算法是一个必考的考点,掌握一些基本的排序算法对于一个前端工程师来说是非常重要的。 排序算法的分类 排序算法可以按照许多不同的标准进行分类: 平均时间复杂度 空间复杂度 稳定性 内部排序和外部排序 在这篇文章中,我们将按照时间复杂度从小到大的顺序介绍以下五个基本的排序算法:插入排序、选择排序、归…

    算法与数据结构 2023年5月19日
    00
  • c语言快速排序算法示例代码分享

    首先,我们需要了解什么是快速排序。快速排序(QuickSort)是一种排序算法,其采用了分治的思想,并使用递归的方式处理数据集合。它的基本思想是从待排序的数据集合中选择一个元素作为分界点(一般称为pivot),然后将小于pivot的元素放到pivot左边,大于pivot的元素放到pivot右边,最后将pivot放到中间位置。然后递归处理pivot左右两边的子…

    算法与数据结构 2023年5月19日
    00
  • 冒泡排序算法及Ruby版的简单实现

    冒泡排序是一种比较简单的排序算法,其基本思想是重复地遍历数列,每次比较相邻的两个元素,如果前一个元素比后一个元素大,则交换这两个元素的位置,直到遍历完整个数列,这样一次遍历后,数列中最大的元素就被排到了最后面。重复执行此过程,直到整个数列有序为止。 以下是冒泡排序算法的Ruby版简单实现: def bubble_sort(array) n = array.l…

    算法与数据结构 2023年5月19日
    00
  • Java 堆排序实例(大顶堆、小顶堆)

    下面我将为您介绍 Java 堆排序实例(大顶堆、小顶堆)的完整攻略。 1. 堆排序介绍 堆排序是一种树形选择排序方法,它的特点是将数组看成一棵完全二叉树,然后通过建立堆(一种特殊的完全二叉树),逐个取出堆顶元素并重新建堆的过程来进行排序。具体来说,堆排序可以分为两种:大顶堆排序和小顶堆排序。 在大顶堆排序中,堆顶元素最大,从小到大进行排序;在小顶堆排序中,堆…

    算法与数据结构 2023年5月19日
    00
  • C++ sort排序之降序、升序使用总结

    C++ sort排序之降序、升序使用总结 介绍 sort函数是C++ STL库提供的一种排序函数,可以快速方便地对数组或容器进行排序。本文将详细介绍sort函数的用法,包括排序方式、自定义比较函数和对容器的排序等内容。 基本用法 sort函数的声明如下: template <class RandomAccessIterator> void sor…

    算法与数据结构 2023年5月19日
    00
  • C语言冒泡排序法的实现(升序排序法)

    冒泡排序是一种简单的排序算法。它会依次比较相邻两个元素,如果它们的顺序错误就交换它们的位置,直到所有元素都排列成功。 以下是C语言冒泡排序的实现过程: 1.先定义数组 代码示例: int a[10] = {23, 56, 12, 45, 9, 17, 98, 67, 41, 3}; 2.开始排序 首先,我们需要使用两层循环来遍历每一个元素。 外层循环从第一个…

    算法与数据结构 2023年5月19日
    00
  • 用c语言实现冒泡排序,选择排序,快速排序

    首先我们来讲一下三种基本的排序算法——冒泡排序、选择排序和快速排序,并且给出实现的具体代码。 冒泡排序 冒泡排序是一个非常简单的排序算法,其基本思想是比较相邻两个数的大小,如果前一个数比后一个数大,就将两个数交换位置。通过不断重复这个过程,将最大的数“冒泡”到数组的最后面,这个过程类似于水泡在水中不断冒上来,因此得其名。 具体的实现代码如下: void bu…

    算法与数据结构 2023年5月19日
    00
  • 深入解析桶排序算法及Node.js上JavaScript的代码实现

    深入解析桶排序算法及Node.js上JavaScript的代码实现 桶排序算法介绍 桶排序算法是一种非常有效的排序方法,通常用于在已知数据范围的情况下对数据进行排序。桶排序将数据分配到一个或多个桶中,然后对每个桶中的数据进行排序,最后将所有桶中的数据依次合并即可得到有序的结果。 桶排序的时间复杂度为O(n),其中n为待排序的数据个数。如果数据范围较大,需要分…

    算法与数据结构 2023年5月19日
    00
合作推广
合作推广
分享本页
返回顶部