Hacker Newsnew | past | comments | ask | show | jobs | submitlogin

> every type must have a default/zero value in Go

Hot take, maybe, but this is one of the few "mistakes" I see with Go. It makes adding QoL things like you mentioned difficult, requires shoehorning pointers to allow for an unset condition, some types don't have a safe default/zero value like maps, and makes comparisons (especially generic) overly complex.



Go specifically does not want to add QoL things because it means the compiler team has to spend time implementing that extra syntax and semantics versus making a minimal set of features better.


The problem with the zero value business is that it also makes adding these QoL things in libraries difficult or outright impossible. Case in point, I tried building a library for refinement types, so you can have a newtype like,

  type AccountName string
except you write it like (abridged)

  type AccountName refined.Scalar[AccountName, string]

  func (AccountName) IsValid(value string) bool {
    return accountNameRegexp.MatchString(value)
  }
and that enforces an invariant through the type system. In this case, any instance of type AccountName needs to hold a string conforming to a certain regular expression. (Another classical example would be "type DiceRoll int" that is restricted to values 1..6.)

But then you run into the problem with the zero value, where the language allows you to say

  var name AccountName // initialized to zero value, i.e. empty string
and now you have an illegal instance floating around (assuming for the sake of argument that the empty string is not a legal account name). You can only really guard against that at runtime, by panic()ing on access to a zero-valued AccountName. Arguably, this could be guarded against with test coverage, but the more insidious variant is

  type AccountInfo struct {
    ID int64 `json:"id"`
    Name AccountName `json:"name"`
  }
When you json.Unmarshal() into that, and the payload does not contain any mention of the "name" field, then AccountName is zero-valued and does not have any chance of noticing. The only at least somewhat feasible solution that I could see was to have a library function that goes over freshly unmarshaled payloads and looks for any zero-valued instances of any refined.Scalar type. But that gets ugly real quick [1], and once again, it requires the developer to remember to do this.

[1] https://github.com/majewsky/gg/blob/refinement-types-4/refin...

So yeah, I do agree that zero values are one of the language's biggest mistakes. But I also agree that this is easier to see with 20 years of hindsight and progress in what is considered mainstream for programming languages. Go was very much trying to be a "better C", and by that metric, consistent zero-valued initialization is better than having fresh variables be uninitialized.


> The only at least somewhat feasible solution that I could see

You can use pointers and then `encoding/json` will leave them as `nil` if the field is missing when you `Unmarshal`. I believe the AWS Go SDK uses this technique for "optional" fields (both input and output.) Obviously more of a faff than if it supported truly "unset" fields but it is what it is.

(see https://go.dev/play/p/rkLqnEmyuVE )


Go was trying to be a better c++. In c++ there are infinity different constructors and that was too complicated, so they made a language with only one constructor. Go isn't the way it is because nobody knew any better, it's because they deliberately chose to avoid adding things that they thought weren't beneficial enough to justify their complexity.


You're missing the point, Go does not want these QoL features. Arguing about why they are hard to add is pointless because, philosophically, they are undesirable and not going to be accepted.


Go 1.26 just added new(expr) which simplifies passing values to places that expect pointers.

The old guard is slowly stepping away, for good or ill. QoL changes are not off the table, but they do have to fit into the language.




Guidelines | FAQ | Lists | API | Security | Legal | Apply to YC | Contact

Search: