gpt4 book ai didi

loops - Golang和结构数组的结构

转载 作者:数据小太阳 更新时间:2023-10-29 03:37:18 26 4
gpt4 key购买 nike

我为电影和电视节目定义了以下结构:

type Movie struct {
ID string `json:"id"`
Viewers int `json:"count"`
}
type TVShow struct {
ID string `json:"id"`
Season int `json:"season"`
Episode int `json:"episode"`
Viewers int `json:"count"`
}

然后,我具有以下结构,其中包含按国家/地区显示的几部电影或电视节目:
type Movies struct {
PenultimateMonth map[string][]Movie
LastMonth map[string][]Movie
}
type TVShows struct {
PenultimateMonth map[string][]TVShow
LastMonth map[string][]TVShow
}

最后,我有一个包含所有内容的数据结构:
type Data struct {
Movies Movies
Seasons Seasons
}

我需要做的是收集倒数第二个和上个月所有电影和电视节目的 所有 ID。

我发现可以为此使用反射,但是我仅设法逐个遍历每个 Data元素,而不是全部遍历:
func GetIDs(data *Data, country string) []string {
var ids []string

movies := reflect.ValueOf(data.Movies).Elem()
tvShows := reflect.ValueOf(data.TVShows).Elem()

for i := 0; i < movies.NumField(); i++ {
moviesSubset := movies.Field(i).Interface().(map[string][]Movie)
for _, movie := range moviesSubset[country] {
ids = append(ids, movie.ID)
}
}

for i := 0; i < tvShows.NumField(); i++ {
tvShowsSubset := tvShows.Field(i).Interface().(map[string][]TVShow)
for _, tvShow := range tvShowsSubset[country] {
ids = append(ids, tvShow.ID)
}
}

return ids
}

是否可以简化 GetIDs函数,以使我不需要两个单独的电影和电视节目块,而只需要一个块来收集所有ID?

最佳答案

使用界面:

type identifiable interface {
GetID() string
}

type identifiables interface {
GetIDs() []string
}

您可以实现如下:
func (m Movie) GetID() string { return m.ID }

并用于多态地收集ID。

您可以为每种类型编写它,或者使映射存储接口并实现一次。
type identifiable interface {
GetID() string
}

type identifiables interface {
GetIDs() []string
}

func (m Movie) GetID() string { return m.ID }

type movies []Movie
type moviesByCountry map[string]movies

func (m movies) GetIDs() (ret []string) {
for _, movie := range m {
ret = append(ret, movie.GetID())
}
return
}

func (m moviesByCountry) GetIDs() (ret []string) {
for _, slice := range m {
ret = append(ret, slice.GetIDs()...)
}
return
}

func (d Data) GetCountryIDs(country string) []string {
return gatherIDs(d.TVShows[country], d.Movies[country])
}

func gatherIDs(collections ...identifiables) (ret []string) {
for _, collection := range collections {
ret = append(ret, collection.GetIDs()...)
}
return
}

这是 working playground example

不是很有效,但是简单一致的恕我直言。如果存在问题,则可以通过传递累加器片来对其进行优化,但我建议您使用 private 方法的接口使用该路由。

我认为应该有一个合理的理由
type identifiableByCountry interface {
GetCountryIDs(string) []string
}

因为 Data和 map 都可以实现。

如果您更喜欢使用lambda,则还可以使用以下方法:
type collection interface {
walk(func(identifiable))
}

并在集合类型上实现它,将其用作
c.walk(func(o identifiable) {
ids = append(ids, o.GetID())
})

关于loops - Golang和结构数组的结构,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/43893474/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com