📌  相关文章
📜  如何在 Golang 中对切片进行排序?(1)

📅  最后修改于: 2023-12-03 15:38:16.069000             🧑  作者: Mango

如何在 Golang 中对切片进行排序?

在 Golang 中,我们可以使用标准库中的 sort 包来对切片进行排序。这个包提供了几种排序算法,可以根据不同的需求选择不同的算法。

sort 包中的排序函数

sort 包中提供了三个排序函数:

  • func Sort(data Interface):用于排序任何实现了 sort.Interface 接口的切片类型。
  • func Stable(data Interface):类似于 Sort,但是会保留相等元素的原本顺序。
  • func IsSorted(data Interface) bool:检查切片是否已经排序。
实现 sort.Interface 接口

为了让我们自定义的类型能够被 sort.Sort() 函数排序,我们需要实现 sort.Interface 接口中的三个方法:

type Interface interface {
    // Len 方法返回集合中的元素个数
    Len() int
    // Less 方法报告索引 i 的元素是否比索引 j 的元素更小
    Less(i, j int) bool
    // Swap 方法交换索引 i 和 j 的两个元素
    Swap(i, j int)
}

例如,我们可以定义一个 Person 结构体,并编写 sort.Interface 接口的实现:

type Person struct {
    Name string
    Age  int
}

type ByAge []Person

func (a ByAge) Len() int           { return len(a) }
func (a ByAge) Less(i, j int) bool { return a[i].Age < a[j].Age }
func (a ByAge) Swap(i, j int)      { a[i], a[j] = a[j], a[i] }

接着,我们就可以使用 sort.Sort() 函数对 ByAge 类型的切片进行排序了:

people := []Person{
    {"Bob", 31},
    {"John", 42},
    {"Michael", 17},
    {"Jenny", 26},
}

sort.Sort(ByAge(people))

fmt.Println(people)
// 输出:[{Michael 17} {Jenny 26} {Bob 31} {John 42}]
示例代码

以下是一个完整的使用 sort 包进行排序的示例:

package main

import (
    "fmt"
    "sort"
)

type Person struct {
    Name string
    Age  int
}

type ByAge []Person

func (a ByAge) Len() int           { return len(a) }
func (a ByAge) Less(i, j int) bool { return a[i].Age < a[j].Age }
func (a ByAge) Swap(i, j int)      { a[i], a[j] = a[j], a[i] }

func main() {
    people := []Person{
        {"Bob", 31},
        {"John", 42},
        {"Michael", 17},
        {"Jenny", 26},
    }

    fmt.Println("Original:", people)

    sort.Sort(ByAge(people))
    fmt.Println("Sorted by Age:", people)

    sort.SliceStable(people, func(i, j int) bool {
        return people[i].Name < people[j].Name
    })
    fmt.Println("Sorted by Name:", people)
}

输出:

Original: [{Bob 31} {John 42} {Michael 17} {Jenny 26}]
Sorted by Age: [{Michael 17} {Jenny 26} {Bob 31} {John 42}]
Sorted by Name: [{Bob 31} {Jenny 26} {John 42} {Michael 17}]
总结

通过实现 sort.Interface 接口,我们可以自定义类型的排序方式;sort 包中的三个排序函数可以实现不同的排序需求,在使用时需要注意保留相等元素顺序的问题。