1. ホーム
  2. sorting

[解決済み] 構造体の配列を(任意の)フィールド名で単純にソートする最短の方法は何ですか?

2022-03-12 07:37:01

質問

構造体の配列がある場合、次のような問題が発生しました。

package main

import "log"

type Planet struct {
    Name       string  `json:"name"`
    Aphelion   float64 `json:"aphelion"`   // in million km
    Perihelion float64 `json:"perihelion"` // in million km
    Axis       int64   `json:"Axis"`       // in km
    Radius     float64 `json:"radius"`
}

func main() {
    var mars = new(Planet)
    mars.Name = "Mars"
    mars.Aphelion = 249.2
    mars.Perihelion = 206.7
    mars.Axis = 227939100
    mars.Radius = 3389.5

    var earth = new(Planet)
    earth.Name = "Earth"
    earth.Aphelion = 151.930
    earth.Perihelion = 147.095
    earth.Axis = 149598261
    earth.Radius = 6371.0

    var venus = new(Planet)
    venus.Name = "Venus"
    venus.Aphelion = 108.939
    venus.Perihelion = 107.477
    venus.Axis = 108208000
    venus.Radius = 6051.8

    planets := [...]Planet{*mars, *venus, *earth}
    log.Println(planets)
}

で並べ替えたいとします。 Axis . どうやるんだ?

(注)私が見たのは http://golang.org/pkg/sort/ というのがあって、それは動作するようですが、非常に単純なキーによる単純なソートのためだけに、20行ほど追加しなければならないのです。私はpythonのバックグラウンドを持っていて、それは以下のように単純です。 sorted(planets, key=lambda n: n.Axis) - は、Goで同じような簡単なものがありますか?)

どのように解決するのですか?

UPDATEしてください。 この回答は、旧バージョンの go . Go 1.8 以降のバージョンについては 上記のAndreKRさんの回答 .


標準ライブラリよりもう少し冗長でないものが欲しい場合 sort パッケージを使用すると、サードパーティの github.com/bradfitz/slice パッケージを使用します。 これは、いくつかのトリックを使って LenSwap メソッドが必要なので、スライスのソートに必要なのは Less メソッドを使用します。

このパッケージを使用すると、ソートを実行することができます。

slice.Sort(planets[:], func(i, j int) bool {
    return planets[i].Axis < planets[j].Axis
})

planets[:] の部分は、配列をカバーするスライスを生成するために必要です。 もし planets を配列ではなくスライスにすることで、この部分を省略することができます。