sorting - go type conversion - 使用共享接口(interface)对 2 片不同的接口(interface)进行排序

标签 sorting go type-conversion

下面的示例包含 2 个接口(interface) FooBar,它们都实现了相同的接口(interface) Timestamper。它还包含实现 sort.Interface 的类型 ByTimestamp .

如函数 main 所示,我想使用类型 ByTimestampFoo 的 slice 和 slice 进行排序条形图。但是,代码将无法编译,因为它无法将 foos(类型 []Foo)转换为 ByTimestamp 类型,并且无法将 bars(类型 []Bar)转换为 ByTimestamp 类型

是否可以使用实现 sort.Interface 的单一类型对实现相同接口(interface)的 2 个不同接口(interface) slice 进行排序?

package main

import (
    "sort"
)

type Timestamper interface {
    Timestamp() int64
}

type ByTimestamp []Timestamper

func (b ByTimestamp) Len() int {
    return len(b)
}

func (b ByTimestamp) Swap(i, j int) {
    b[i], b[j] = b[j], b[i]
}

func (b ByTimestamp) Less(i, j int) bool {
    return b[i].Timestamp() < b[j].Timestamp()
}

type Foo interface {
    Timestamper
    DoFoo() error
}

type Bar interface {
    Timestamper
    DoBar() error
}

func getFoos() (foos []Foo) {
    // TODO get foos
    return
}

func getBars() (bars []Bar) {
    // TODO get bars
    return
}

func main() {
    foos := getFoos()
    bars := getBars()

    sort.Sort(ByTimestamp(foos))
    sort.Sort(ByTimestamp(bars))
}

The Go playground

最佳答案

是的,可以使用一个sort.Interface 对不同类型进行排序。 但不是你试图做的方式。当前的 Go 规范不允许将一种 slice 类型转换为另一种 slice 类型。您必须转换每个项目。

这是一个使用反射完成它的辅助函数:

// ByTimestamp converts a slice of Timestamper into a slice
// that can be sorted by timestamp.
func ByTimestamp(slice interface{}) sort.Interface {
    value := reflect.ValueOf(slice)
    length := value.Len()
    b := make(byTimestamp, 0, length)
    for i := 0; i < length; i++ {
        b = append(b, value.Index(i).Interface().(Timestamper))
    }
    return b
}

查看完整示例 here .

而且,如果您只有几种类型,那么进行特定于类型的转换可能更有意义。

关于sorting - go type conversion - 使用共享接口(interface)对 2 片不同的接口(interface)进行排序,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49341895/

相关文章:

google-app-engine - 如何验证 appengine.SignBytes 返回的签名?

Golang 排序接口(interface) slice

vb.net - 在 VB 中对列表框项目进行数字排序

c++ - 如何使用区分大小写的元素对 std::list 进行排序?

go - 带有到期日期代码的认证代码

go - 是否有可能知道 Go 中函数的返回值类型?

crystal-reports - 将 int 转换为字符串的 Crystal 报告问题

c++ - 如何在 C++ 中获取具有给定位模式(如 int32_t)的 float ?

C# 按枚举排序列表

java - 什么是对文件中数百万行整数进行排序的有效算法?