Max, apparently you didn’t understand what Maxime’s proposal is *at all*.
For example, he didn’t propose anything that would change the existence of this type: type Direction = Up | Down | Left | Right 2017-01-15 23:47 GMT+01:00 Max Goldstein <[email protected]>: > First, I appreciate that this proposal is being made in the spirit of Elm: > seeking to simplify the language, with reference to existing usage (red > sentence in the first post), and trying to solve an existing problem > (serialization of union types). It's clear that Maxime wants to learn and > improve the language. Thank you. > > So let's look at how union types are used, what jobs they are hired to do, > if you will. You've noticed in core that union types with one tag are used > to hide things. Sometimes that's as an opaque type: there is one tag that's > not exposed, and is pattern-matched easily, and the data the tag holds can > change even in a patch release (example here > <https://github.com/mgold/elm-animation/blob/master/Animation.elm#L89-L105>). > Core also contains a rare pattern of, say *type Task x a = Task* where > the *Task* value defined is not actually used anywhere because it's > actually a native implementation. Serializing arbitrary union types will > have to account for this case. > > A more realistic use of union types is as a finite set of labels, even if > these labels don't carry any information along with them. For example: > > type Direction = Up | Down | Left | Right > > From this we derive pattern matches with static > (compile-time) exhaustiveness checking, which is a huge improvement in > reliability and refactorability over "stringly typed" conventions (instead > of strongly typed, get it?) that you'll see in JavaScript and the like. > Replacing the Direction type with a record including a string removes this > huge improvement. > > Adding data to these tags allows for the classic use case of data that > only makes sense in certain contexts. I remember working with a C++ > graphics library where certain fields of structs were only defined if an > enum was set to a particular value. But this isn't really a separate use > case from labels without data, since you can freely mix within a type. The > RemoteData > type > <http://package.elm-lang.org/packages/krisajenkins/remotedata/4.2.1/RemoteData#RemoteData>does > this to great effect. > > More theoretically, union types and records are not the same; they are > actually duals. Union types are referred to as "sum types" and records (and > tuples) are "product types". Here's the reasoning: consider two types, *a* > and *b*. Let's denote the number of values of type *a* as |a|, and > similarly |b|. If we construct the sum type *Result a b* then there are > |a| values for the Err case and |b| values for the Ok case. So |Result a b| > = |a| + |b|, hence sum types. For the pair (a, b) we can pick any *a* and > any *b* so |(a,b)| = |a|*|b|, hence produce types. > > If you want to produce (create) a value of sum type, such as *Result a b*, > you can pick either case to work with. But when you consume (inspect) a > value of that type, you must be prepared to handle all cases. For product > types it is reversed: to produce a value of type (a,b) you must have both > an *a* and a *b*, but when you consume such a value, you can pick out the > one you want. > > So, while I appreciate the gesture, I don't think this will work. > > -- > You received this message because you are subscribed to the Google Groups > "Elm Discuss" group. > To unsubscribe from this group and stop receiving emails from it, send an > email to [email protected]. > For more options, visit https://groups.google.com/d/optout. > -- You received this message because you are subscribed to the Google Groups "Elm Discuss" group. To unsubscribe from this group and stop receiving emails from it, send an email to [email protected]. For more options, visit https://groups.google.com/d/optout.
