4 ms·
This tries to sound profound but it really just misunderstands basic sum types. In Rust/Haskell/etc you're free to return multiple values if that's even potenti
by awused 3y ago
This tries to sound profound but it really just misunderstands basic sum types. In Rust/Haskell/etc you're free to return multiple values if that's even potentially useful. If you have a function that can completely fail, partially fail (in this example, opening a file but then something else fails), or entirely succeed, you can encode that in the type system. In Go you cannot define this in the type system, you just have comments explaining how it works and hoping both that you implement it correctly and callers of your code read and understand them. If your code does return both files and errors in some cases, chances are callers are going to handle it incorrectly, especially if, say, the caller is responsible for closing files/responses/streams/etc.
In Rust/Haskell I can write a type with three values like Success(file), PartialSuccess(file, error), or Failure(error). Callers must then handle all of these. In Go I always have four cases for a simple function including those three and the final case of neither file nor error. Most Go callers will not handle the case where err != nil and file != nil and often the case where err == nil and file == nil will cause a panic and crash the program.
There was a tradeoff for this, but in this case the tradeoff was entirely in making the Go compiler simpler at the cost of making the Go language weaker and Go code more error-prone.