package main import ( "strings" ) type gotype struct { SliceOf *gotype MapKey *gotype MapVal *gotype PtrTo *gotype IsFunc bool FuncParams []gotype FuncReturn []gotype Plain string // TODO channel-of (although we will never? construct one from PHP source) } func goTypeListToString(gotypes []gotype) string { ret := make([]string, 0, len(gotypes)) for _, gt := range gotypes { ret = append(ret, gt.AsGoString()) } return strings.Join(ret, `, `) } func (gt gotype) AsGoString() string { if gt.SliceOf != nil { return "[]" + gt.SliceOf.AsGoString() } else if gt.MapKey != nil { return "map[" + gt.MapKey.AsGoString() + "]" + gt.MapVal.AsGoString() } else if gt.PtrTo != nil { return "*" + gt.PtrTo.AsGoString() } else if gt.IsFunc { ret := "func(" + goTypeListToString(gt.FuncParams) + `)` if len(gt.FuncReturn) == 1 { ret += ` ` + gt.FuncReturn[0].AsGoString() } else if len(gt.FuncReturn) >= 2 { ret += ` (` + goTypeListToString(gt.FuncReturn) + `)` } return ret } else { return gt.Plain } } func (gt gotype) IsPlain() bool { if gt.SliceOf != nil || gt.MapKey != nil || gt.PtrTo != nil || gt.IsFunc { return false } return true } func (gt gotype) Equals(other *gotype) bool { return gt.AsGoString() == other.AsGoString() } // ZeroValue returns a Go literal string for the zero value of this type. func (gt gotype) ZeroValue() string { if !gt.IsPlain() { return `nil` } // It's a plain type switch gt.Plain { case "byte", "int", "int8", "int16", "int32", "int64", "uint", "uint8", "uint16", "uint32", "uint64", "float", "float64": return `0` case "bool": return `false` case "string": return `""` case "rune": return `''` default: // probably a struct type return gt.AsGoString() + `{}` } }