Right, I discussed that: Currently, if I understand correctly, the only way to do this is to declare > a variable, and return that: > var zeroValue V > return zeroValue
On Mon, May 30, 2022 at 7:33 PM Bruno Albuquerque <b...@gmail.com> wrote: > This should work on your example: > > var zeroValue V > > On Mon, May 30, 2022, 6:39 PM Will Faught <w...@willfaught.com> wrote: > >> Hello, fellow Gophers! >> >> Currently, if I understand correctly, there's no expression for the zero >> value for a type variable: >> >> type Map[K comparable, V any] struct { >> ks []K >> vs []V >> } >> >> func (m Map[K, V]) Get(k K) V { >> for i, k2 := range m.ks { >> if k2 == k { >> return m.vs[i] >> } >> } >> return zeroValue // cannot currently express this >> } >> >> This is a trivial example, but I've seen real questions about what to do >> in these situations. >> >> Currently, if I understand correctly, the only way to do this is to >> declare a variable, and return that: >> >> var zeroValue V >> return zeroValue >> >> Why not allow nil to be used as the zero value for type variables, to >> fill this gap? >> >> return nil // == V(nil) >> >> At runtime, nil would be the zero value for the specific type argument. >> >> Nil could actually be interpreted as the zero value for every type, even >> outside of generics. The word "nil" means >> <https://en.wiktionary.org/wiki/nil#Noun> zero, anyway. This would be >> handy in situations where you make a type a pointer just to avoid lots of >> typing. For example: >> >> if condition1 { >> return ReallyLongStructName{}, fmt.Errorf(...) >> } >> if condition2 { >> return ReallyLongStructName{}, fmt.Errorf(...) >> } >> >> Instead, you could keep the non-pointer type, and then do: >> >> if condition1 { >> return nil, fmt.Errorf(...) >> } >> if condition2 { >> return nil, fmt.Errorf(...) >> } >> >> It would also solidify the type abstraction concept of generic functions, >> where functions varying only in concrete types can be abstracted into one >> generic function with type variables. For example: >> >> // Same implementations, different types >> >> func (m MapIntInt) Get(k int) int { >> for i, k2 := range m.ks { >> if k2 == k { >> return m.vs[i] >> } >> } >> return nil // nil, not 0, but means the same thing for int >> } >> >> func (m MapStringString) Get(k string) string { >> for i, k2 := range m.ks { >> if k2 == k { >> return m.vs[i] >> } >> } >> return nil // nil, not "", but means the same thing for string >> } >> >> // Same implementation, abstracted types >> >> func (m Map[K, V]) Get(k K) V { >> for i, k2 := range m.ks { >> if k2 == k { >> return m.vs[i] >> } >> } >> return nil // nil is 0 for int and "" for string >> } >> >> Similar to how generics required an inversion of the meaning of >> interfaces to be type sets, perhaps generics also requires an inversion of >> the meaning of zero and nil values, where every type has a nil (default) >> value, and for number-like types, that just so happens to be the number >> zero, but for other types, it could be whatever makes sense for them. >> >> Anyway, I thought it was an interesting idea. Thanks for reading! >> >> -- >> You received this message because you are subscribed to the Google Groups >> "golang-nuts" group. >> To unsubscribe from this group and stop receiving emails from it, send an >> email to golang-nuts+unsubscr...@googlegroups.com. >> To view this discussion on the web visit >> https://groups.google.com/d/msgid/golang-nuts/CAKbcuKjePVMPH1Fxv3tWAAm_msjAZKmtbJs2EMkQ7WGEgtAqyA%40mail.gmail.com >> <https://groups.google.com/d/msgid/golang-nuts/CAKbcuKjePVMPH1Fxv3tWAAm_msjAZKmtbJs2EMkQ7WGEgtAqyA%40mail.gmail.com?utm_medium=email&utm_source=footer> >> . >> > -- You received this message because you are subscribed to the Google Groups "golang-nuts" group. To unsubscribe from this group and stop receiving emails from it, send an email to golang-nuts+unsubscr...@googlegroups.com. To view this discussion on the web visit https://groups.google.com/d/msgid/golang-nuts/CAKbcuKitNRH2NBSySY%2BReGzKDgyhapAW5D24XT-OvULDrcsB%3Dw%40mail.gmail.com.