为切片没有长度的结构切片赋值
Assign value to slice of struct which the slice have no length
我有一段结构来容纳来自数据库的数据。我的结构如下所示:
type TempGigs struct {
Id int `json:"id" db:"id"`
Title string `json:"title" db:"title"`
UserID int `json:"user_id" db:"user_id"`
Price int `json:"price" db:"price"`
Currency string `json:"currency" db:"currency"`
Username string `json:"username" db:"username"`
ImageProfile string `json:"image_profile" db:"image_profile"`
Level string `json:"level" db:"level"`
GigRating float64 `json:"gig_rating" db:"gig_rating"`
TotalReview int `json:"total_review" db:"total_review"`
CreatedAt int `json:"created_at" db:"created_at"`
Favorite bool `json:"favorite" db:"favorite"`
}
我想将数据从 []TempGigs
移动到 []Gigs
。 Gigs
结构定义为:
type ResponseGigs struct {
SectionName string `json:"section_name"`
Offset int `json:"offset"`
Limit int `json:"limit"`
TotalRows int `json:"total_rows"`
Gigs []struct {
SellerInfo struct {
UserID int `json:"user_id"`
Username string `json:"username"`
Name string `json:"name"`
ImageProfile string `json:"image_profile"`
Level string `json:"level"`
} `json:"seller_info"`
ID int `json:"id" db:"id"`
Title string `json:"title" db:"title"`
Medias []struct {
ID int `json:"id"`
Name string `json:"name"`
TypeFile string `json:"type_file"`
ImageURL string `json:"image_url"`
} `json:"medias"`
Price int `json:"price"`
Currency string `json:"currency"`
Rating struct {
AVGRating float64 `json:"avg_rating"`
TotalReviews int `json:"total_reviews"`
} `json:"rating"`
Favorite bool `json:"favorite"`
} `json:"gigs"`
}
当我用for
迭代TempGigs
复制到[]Gigs
时,编译时没有错误。但是,当提交请求时,程序会出现 panic: runtime error: index out of range [0] with length 0
恐慌。
我试过使用 append
但我不明白如何正确使用 append
。
这是我的迭代代码:
tempGigs := []TempGigs{}
tempResp := ResponseGigs{}
tempResp.SectionName = "Best seller"
tempResp.Offset = 0
tempResp.Limit = 10
for i := range tempGigs {
tempResp.Gigs[i].SellerInfo.UserID = tempGigs[i].UserID
tempResp.Gigs[i].SellerInfo.Name = tempGigs[i].Username
tempResp.Gigs[i].SellerInfo.ImageProfile = fmt.Sprintf("%s/%s", os.Getenv("STORAGE_URL"), tempGigs[i].ImageProfile)
tempResp.Gigs[i].SellerInfo.Level = tempGigs[i].Level
tempResp.Gigs[i].ID = tempGigs[i].Id
tempResp.Gigs[i].Title = tempGigs[i].Title
tempResp.Gigs[i].Price = tempGigs[i].Price
tempResp.Gigs[i].Currency = tempGigs[i].Currency
tempResp.Gigs[i].Rating.AVGRating = tempGigs[i].GigRating
tempResp.Gigs[i].Rating.TotalReviews = tempGigs[i].TotalReview
tempResp.Gigs[i].Favorite = tempGigs[i].Favorite
}
utils.HTTPJsonSuccess(w, http.StatusOK, tempGigs)
return
你的问题已经在评论中得到了正确的回答,但也许它可以帮助你获得更多关于你的代码的反馈。
从结构中提取子类型
ResponseGigs
是一个具有多个子结构的大型结构,这使得它很难使用。将子结构提取为额外类型使事情变得更容易。
type ResponseGigs struct {
SectionName string `json:"section_name"`
Offset int `json:"offset"`
Limit int `json:"limit"`
TotalRows int `json:"total_rows"`
Gigs []Gig `json:"gigs"`
}
type Gig struct {
SellerInfo SellerInfo `json:"seller_info"`
ID int `json:"id" db:"id"`
Title string `json:"title" db:"title"`
Medias []Media `json:"medias"`
Price int `json:"price"`
Currency string `json:"currency"`
Rating Rating `json:"rating"`
Favorite bool `json:"favorite"`
}
type SellerInfo struct {
UserID int `json:"user_id"`
Username string `json:"username"`
Name string `json:"name"`
ImageProfile string `json:"image_profile"`
Level string `json:"level"`
}
type Media struct {
ID int `json:"id"`
Name string `json:"name"`
TypeFile string `json:"type_file"`
ImageURL string `json:"image_url"`
}
type Rating struct {
AVGRating float64 `json:"avg_rating"`
TotalReviews int `json:"total_reviews"`
}
type TempGig struct {
Id int `json:"id" db:"id"`
Title string `json:"title" db:"title"`
UserID int `json:"user_id" db:"user_id"`
Price int `json:"price" db:"price"`
Currency string `json:"currency" db:"currency"`
Username string `json:"username" db:"username"`
ImageProfile string `json:"image_profile" db:"image_profile"`
Level string `json:"level" db:"level"`
GigRating float64 `json:"gig_rating" db:"gig_rating"`
TotalReview int `json:"total_review" db:"total_review"`
CreatedAt int `json:"created_at" db:"created_at"`
Favorite bool `json:"favorite" db:"favorite"`
}
创建一个额外的函数将 TempGig
转换为 Gig
接下来我要做的是创建一个将 TempGig
转换为 Gig
的函数。 (我将 TempGigs
重命名为 TempGig
,因为该结构只包含一个演出,而不是多个演出):
func toGig(in TempGig) Gig {
return Gig{
SellerInfo: SellerInfo{
UserID: in.UserID,
Name: in.Username,
ImageProfile: in.ImageProfile,
Level: in.Level,
},
ID: in.Id,
Title: in.Title,
// ...
}
}
填写回复slice
为了尽量减少处理程序代码,我还创建了一个额外的函数来构建 ResponseGigs
结构。例如:
func toResponse(section string, in []TempGig) ResponseGigs {
var gigs []Gig
// or to preallocate the memory space / capacity (not the length!)
// gigs := make([]Gig, 0, len(in))
for _, tempGig := range in {
gigs = append(gigs, toGig(tempGig))
}
return ResponseGigs{
SectionName: section,
Gigs: gigs,
}
}
或者,您可以预先分配切片的长度并使用索引。我更喜欢 append
方法,因为它不太容易出错。
// preallocate the length of the slice (not only the capacity)
gigs := make([]Gig, len(in))
for i, tempGig := range in {
gigs[i] = toGig(tempGig)
}
处理程序代码
最后,处理程序代码将归结为如下内容:
tempResp := toReponse("Best seller", tempGigs)
tempResp.Offset = 0
tempResp.Limit = 10
utils.HTTPJsonSuccess(w, http.StatusOK, tempResp)
return
希望这对下一步有所帮助。有很多东西可以根据自己的喜好进行调整。编码愉快!
我有一段结构来容纳来自数据库的数据。我的结构如下所示:
type TempGigs struct {
Id int `json:"id" db:"id"`
Title string `json:"title" db:"title"`
UserID int `json:"user_id" db:"user_id"`
Price int `json:"price" db:"price"`
Currency string `json:"currency" db:"currency"`
Username string `json:"username" db:"username"`
ImageProfile string `json:"image_profile" db:"image_profile"`
Level string `json:"level" db:"level"`
GigRating float64 `json:"gig_rating" db:"gig_rating"`
TotalReview int `json:"total_review" db:"total_review"`
CreatedAt int `json:"created_at" db:"created_at"`
Favorite bool `json:"favorite" db:"favorite"`
}
我想将数据从 []TempGigs
移动到 []Gigs
。 Gigs
结构定义为:
type ResponseGigs struct {
SectionName string `json:"section_name"`
Offset int `json:"offset"`
Limit int `json:"limit"`
TotalRows int `json:"total_rows"`
Gigs []struct {
SellerInfo struct {
UserID int `json:"user_id"`
Username string `json:"username"`
Name string `json:"name"`
ImageProfile string `json:"image_profile"`
Level string `json:"level"`
} `json:"seller_info"`
ID int `json:"id" db:"id"`
Title string `json:"title" db:"title"`
Medias []struct {
ID int `json:"id"`
Name string `json:"name"`
TypeFile string `json:"type_file"`
ImageURL string `json:"image_url"`
} `json:"medias"`
Price int `json:"price"`
Currency string `json:"currency"`
Rating struct {
AVGRating float64 `json:"avg_rating"`
TotalReviews int `json:"total_reviews"`
} `json:"rating"`
Favorite bool `json:"favorite"`
} `json:"gigs"`
}
当我用for
迭代TempGigs
复制到[]Gigs
时,编译时没有错误。但是,当提交请求时,程序会出现 panic: runtime error: index out of range [0] with length 0
恐慌。
我试过使用 append
但我不明白如何正确使用 append
。
这是我的迭代代码:
tempGigs := []TempGigs{}
tempResp := ResponseGigs{}
tempResp.SectionName = "Best seller"
tempResp.Offset = 0
tempResp.Limit = 10
for i := range tempGigs {
tempResp.Gigs[i].SellerInfo.UserID = tempGigs[i].UserID
tempResp.Gigs[i].SellerInfo.Name = tempGigs[i].Username
tempResp.Gigs[i].SellerInfo.ImageProfile = fmt.Sprintf("%s/%s", os.Getenv("STORAGE_URL"), tempGigs[i].ImageProfile)
tempResp.Gigs[i].SellerInfo.Level = tempGigs[i].Level
tempResp.Gigs[i].ID = tempGigs[i].Id
tempResp.Gigs[i].Title = tempGigs[i].Title
tempResp.Gigs[i].Price = tempGigs[i].Price
tempResp.Gigs[i].Currency = tempGigs[i].Currency
tempResp.Gigs[i].Rating.AVGRating = tempGigs[i].GigRating
tempResp.Gigs[i].Rating.TotalReviews = tempGigs[i].TotalReview
tempResp.Gigs[i].Favorite = tempGigs[i].Favorite
}
utils.HTTPJsonSuccess(w, http.StatusOK, tempGigs)
return
你的问题已经在评论中得到了正确的回答,但也许它可以帮助你获得更多关于你的代码的反馈。
从结构中提取子类型
ResponseGigs
是一个具有多个子结构的大型结构,这使得它很难使用。将子结构提取为额外类型使事情变得更容易。
type ResponseGigs struct {
SectionName string `json:"section_name"`
Offset int `json:"offset"`
Limit int `json:"limit"`
TotalRows int `json:"total_rows"`
Gigs []Gig `json:"gigs"`
}
type Gig struct {
SellerInfo SellerInfo `json:"seller_info"`
ID int `json:"id" db:"id"`
Title string `json:"title" db:"title"`
Medias []Media `json:"medias"`
Price int `json:"price"`
Currency string `json:"currency"`
Rating Rating `json:"rating"`
Favorite bool `json:"favorite"`
}
type SellerInfo struct {
UserID int `json:"user_id"`
Username string `json:"username"`
Name string `json:"name"`
ImageProfile string `json:"image_profile"`
Level string `json:"level"`
}
type Media struct {
ID int `json:"id"`
Name string `json:"name"`
TypeFile string `json:"type_file"`
ImageURL string `json:"image_url"`
}
type Rating struct {
AVGRating float64 `json:"avg_rating"`
TotalReviews int `json:"total_reviews"`
}
type TempGig struct {
Id int `json:"id" db:"id"`
Title string `json:"title" db:"title"`
UserID int `json:"user_id" db:"user_id"`
Price int `json:"price" db:"price"`
Currency string `json:"currency" db:"currency"`
Username string `json:"username" db:"username"`
ImageProfile string `json:"image_profile" db:"image_profile"`
Level string `json:"level" db:"level"`
GigRating float64 `json:"gig_rating" db:"gig_rating"`
TotalReview int `json:"total_review" db:"total_review"`
CreatedAt int `json:"created_at" db:"created_at"`
Favorite bool `json:"favorite" db:"favorite"`
}
创建一个额外的函数将 TempGig
转换为 Gig
接下来我要做的是创建一个将 TempGig
转换为 Gig
的函数。 (我将 TempGigs
重命名为 TempGig
,因为该结构只包含一个演出,而不是多个演出):
func toGig(in TempGig) Gig {
return Gig{
SellerInfo: SellerInfo{
UserID: in.UserID,
Name: in.Username,
ImageProfile: in.ImageProfile,
Level: in.Level,
},
ID: in.Id,
Title: in.Title,
// ...
}
}
填写回复slice
为了尽量减少处理程序代码,我还创建了一个额外的函数来构建 ResponseGigs
结构。例如:
func toResponse(section string, in []TempGig) ResponseGigs {
var gigs []Gig
// or to preallocate the memory space / capacity (not the length!)
// gigs := make([]Gig, 0, len(in))
for _, tempGig := range in {
gigs = append(gigs, toGig(tempGig))
}
return ResponseGigs{
SectionName: section,
Gigs: gigs,
}
}
或者,您可以预先分配切片的长度并使用索引。我更喜欢 append
方法,因为它不太容易出错。
// preallocate the length of the slice (not only the capacity)
gigs := make([]Gig, len(in))
for i, tempGig := range in {
gigs[i] = toGig(tempGig)
}
处理程序代码
最后,处理程序代码将归结为如下内容:
tempResp := toReponse("Best seller", tempGigs)
tempResp.Offset = 0
tempResp.Limit = 10
utils.HTTPJsonSuccess(w, http.StatusOK, tempResp)
return
希望这对下一步有所帮助。有很多东西可以根据自己的喜好进行调整。编码愉快!