Comment by Quekid5
6 years ago
I generally like this approach, but it's unfortunately really cumbersome in most mainstream languages like Java (and even Scala 2.x) or C#, but it works beautifully in Haskell because of two features:
- non-exported newtypes (also known as opaque types in Scala 3.x); this means your little module is in full control of instantiation of a 'parsed' value from an 'untyped' value. - DerivingVia (not sure if there's an equivalent in Scala 3.x); this makes declaring type class instances equivalent to the 'wrapped' value completely trivial.
These two features (and, I guess, the pervasiveness of type classes) in Haskell make this sort of thing as close to zero effort as possible.
EDIT: Looking at some sibling posts, I think my C# knowledge may be out of date. Apologies for that.
I think you mean GeneralizedNewtypeDeriving, not DerivingVia. GND lets you pull instances through a newtype, trivially. DerivingVia lets you define your instance in terms of an instance on another newtype.
DerivingVia is a generalization of GeneralizedNewtypeDeriving. The former can do everything the latter can and more. https://downloads.haskell.org/~ghc/latest/docs/html/users_gu...
Exactly. I intentionally avoid GND because it can be quite wonky, and DerivingVia basically subsumes it. You do still have to have slightly more explicit declarations of instances, but IMO it's worth it for the control.