I was reading about struct ordering to save memory. I got below TatProduct struct which I am trying to reorder so that I can save some memory but I am not able to figure out on how to order it so that I can save memory?
type CustomerData struct {
Name map[Customer]map[int]string
}
type Customer string
type TatProduct struct {
Ptr string
ProductId int64
Catalogs []int32
Categories []int
BaseProductId *int64
Code int
IsCurrent bool
CommonValue
}
type YeatStringValue struct {
Value string
ClientId int64
}
type CommonValue struct {
Stuff []YeatStringValue
Carts []YeatStringValue
CustomerData
}
Is there any utility that can help me analyze my struct?
Related
This question already has answers here:
How to initialize a nested struct?
(10 answers)
Initialize nested struct definition
(3 answers)
Closed last year.
I have generated go struct from json.
And it gave me next output:
type PartnerBody87 struct {
Imp []struct {
Bidfloor float64 `json:"bidfloor"`
Secure int `json:"secure"`
Ext struct {
Type string `json:"type"`
Webpush int `json:"webpush"`
} `json:"ext"`
ID string `json:"id"`
Tagid string `json:"tagid"`
} `json:"imp"`
}
I tried different ways, and cannot find proper one of how to initiate the value for
Imp []struct.
Update:
I know that I can split struct into few types. But I'm curious if Go have ability to set everything in 1 struct - than how to use it?
You can split them like this:
type PartnerBody87 struct {
Imp []Imp `json:"imp"`
}
type Imp struct {
Bidfloor float64 `json:"bidfloor"`
Secure int `json:"secure"`
Ext Ext `json:"ext"`
ID string `json:"id"`
Tagid string `json:"tagid"`
}
type Ext struct {
Type string `json:"type"`
Webpush int `json:"webpush"`
}
Here are the Struct relations:
type A struct {
Id int64
RelB []B `gorm:"FOREIGNKEY:Aid;ASSOCIATION_FOREIGNKEY:Id"`
}
type B strcut {
Id int64
Aid int64
RelC []C `gorm:"FOREIGNKEY:Bid;ASSOCIATION_FOREIGNKEY:Id"`
}
type C struct {
Id int64
Bid int64
RelD []D `gorm:"FOREIGNKEY:Cid;ASSOCIATION_FOREIGNKEY:Id"`
}
type D struct {
Id int64
Cid int64
}
I try to find all of these relations with Preload like this:
var result []A
db.Preload("RelB").Preload("RelB.RelC"). // if only three structs relations it works fine so far
Preload("RelB.RelC.RelD"). // it shows errors can not preload field RelD for A
Find(&result)
So, How to relate these four structs with preload? Or there is other better way?
Thanks
Playground for my problem: https://play.golang.org/p/rVwEaxpkJGL
I have struct like
type SimpleBbInput struct {
MyInput struct {
Num struct {
val int
}
}
HisInput string
HerInput uint8
}
I will store the field name and type in a map[string]interface{}, result like
map[HerInput:uint8 MyInput:map[Num:map[val:int]] HisInput:string]
My question is how to using this map to get back SimpleBbInput without knowing this struct.
Thanks
I'm in the process of cleaning some code up and am trying to pass a slice value which is a struct to a function.
My struct looks like this:
type GetRecipesPaginatedResponse struct {
Total int `json:"total"`
PerPage int `json:"per_page"`
CurrentPage int `json:"current_page"`
LastPage int `json:"last_page"`
NextPageURL string `json:"next_page_url"`
PrevPageURL interface{} `json:"prev_page_url"`
From int `json:"from"`
To int `json:"to"`
Data []struct {
ID int `json:"id"`
ParentRecipeID int `json:"parent_recipe_id"`
UserID int `json:"user_id"`
Name string `json:"name"`
Description string `json:"description"`
IsActive bool `json:"is_active"`
IsPublic bool `json:"is_public"`
CreatedAt time.Time `json:"created_at"`
UpdatedAt time.Time `json:"updated_at"`
BjcpStyle struct {
SubCategoryID string `json:"sub_category_id"`
CategoryName string `json:"category_name"`
SubCategoryName string `json:"sub_category_name"`
} `json:"bjcp_style"`
UnitType struct {
ID int `json:"id"`
Name string `json:"name"`
} `json:"unit_type"`
} `json:"data"`
}
In my code, I fetch some JSON data from an API and get a response back that contains about 100 items in the Data slice.
I am then looping over each item in the Data slice and processing them.
As an example, it looks something like this:
for page := 1; page < 3; page++ {
newRecipes := getFromRecipesEndpoint(page, latestTimeStamp) //this returns an instance of GetRecipesPaginatedResponse
for _, newRecipe := range newRecipes.Data {
if rowExists(db, "SELECT id from community_recipes WHERE id=#id", sql.Named("id", newRecipe.ID)) {
insertIntoRecipes(db, true, newRecipe)
} else {
insertIntoRecipes(db, false, newRecipe)
}
}
}
So I am trying to pass the instance of a recipe to the insertIntoRecipes function, which looks like this:
func insertIntoRecipes(db *sql.DB, exists bool, newRecipe GetRecipesPaginatedResponse.Data) {
if exists {
//update the existing record in the DB
//perform some other updates with the information
} else {
//insert a new record into the DB
//insert some other information using this information
}
}
When I run this, I get the error:
GetRecipesPaginatedResponse.Data undefined (type GetRecipesPaginatedResponse has no method Data)
I can tell that the issue is to do with how I am trying to pass the newRecipe to the insertIntoRecipes function, newRecipe GetRecipesPaginatedResponse.Data, however I am not quite sure how to pass it in and declare the right variable type.
To pass an item inside the Data slice to a function, when I am looping over each item of the Data slice, how do I do that?
You cannot reference the anonymous type of the Data field using a field selector. The fix is to declare a named type for the Data field:
type GetRecipesPaginatedResponse struct {
...
Data []DataItem
...
}
type DataItem struct {
ID int `json:"id"`
ParentRecipeID int `json:"parent_recipe_id"`
UserID int `json:"user_id"`
Name string `json:"name"`
...
}
Use it like this:
func insertIntoRecipes(db *sql.DB, exists bool, newRecipe DataItem) {
...
}
There's probably a better name for DataItem.
I have the following structs...
type Menu struct {
Id string `protobuf:"bytes,1,opt,name=id" json:"id,omitempty"`
Name string `protobuf:"bytes,2,opt,name=name" json:"name,omitempty"`
Description string `protobuf:"bytes,3,opt,name=description" json:"description,omitempty"`
Mixers []*Mixer `protobuf:"bytes,4,rep,name=mixers" json:"mixers,omitempty"`
Sections []*Section `protobuf:"bytes,5,rep,name=sections" json:"sections,omitempty"`
}
And...
type Menu struct {
ID bson.ObjectId `json:"id" bson:"_id"`
Name string `json:"name" bson:"name"`
Description string `json:"description" bson:"description"`
Mixers []Mixer `json:"mixers" bson:"mixers"`
Sections []Section `json:"sections" bson:"sections"`
}
I basically need to convert between the two struct types, I've attempted to use mergo, but that can only merge structs that are assignable to one another. The only solution I have so far is iterating through each struct, converting the ID by re-assigning it and converting its type between string and bson.ObjectId. Then iterating through each map field and doing the same. Which feels like an inefficient solution.
So I'm attempting to use reflection to be more generic in converting between the two ID's. But I can't figure out how I can effectively merge all of the other fields that do match automatically, so I can just worry about converting between the ID types.
Here's the code I have so far...
package main
import (
"fmt"
"reflect"
"gopkg.in/mgo.v2/bson"
)
type Sub struct {
Id bson.ObjectId
}
type PbSub struct {
Id string
}
type PbMenu struct {
Id string
Subs []PbSub
}
type Menu struct {
Id bson.ObjectId
Subs []Sub
}
func main() {
pbMenus := []*PbMenu{
&PbMenu{"1", []PbSub{PbSub{"1"}}},
&PbMenu{"2", []PbSub{PbSub{"1"}}},
&PbMenu{"3", []PbSub{PbSub{"1"}}},
}
newMenus := Serialise(pbMenus)
fmt.Println(newMenus)
}
type union struct {
PbMenu
Menu
}
func Serialise(menus []*PbMenu) []Menu {
newMenus := []Menu{}
for _, v := range menus {
m := reflect.TypeOf(*v)
fmt.Println(m)
length := m.NumField()
for i := 0; i < length; i++ {
field := reflect.TypeOf(v).Field(i)
fmt.Println(field.Type.Kind())
if field.Type.Kind() == reflect.Map {
fmt.Println("is map")
}
if field.Name == "Id" && field.Type.String() == "string" {
// Convert ID type
id := bson.ObjectId(v.Id)
var dst Menu
dst.Id = id
// Need to merge other matching struct fields
newMenus = append(newMenus, dst)
}
}
}
return newMenus
}
I'm can't just manually re-assign the fields because I'm hoping to detect maps on the structs fields and recursively perform this function on them, but the fields won't be the same on embedded structs.
Hope this makes sense!
I think that it is probably better to write your own converter, because you will always have some cases that are not covered by existing libs\tools for that.
My initial implementation of it would be something like this: basic impl of structs merger