This sounds very similar to O'Caml's polymorphic variants, which you can
read about here:
http://caml.inria.fr/pub/docs/manual-ocaml/manual006.html#toc36. That link
goes through some of the positives and negatives with the approach.


On Tue, Aug 27, 2013 at 3:58 PM, Bill Myers <bill_my...@outlook.com> wrote:

> I was reading a proposal about adding "datasort refinements" to make enum
> variants first-class types, and it seems to me there is a simpler and more
> effective way of solving the problem.
>
> The idea is that if A, B and C are types, then "A | B | C" is a
> "structural" enum type that can be either A, B or C.
>
> In addition, A can be implicitly converted to "A | B", "A | B" can be
> implicitly converted to "A | B | C", and also "(A | B) | C" and "A | (B |
> C)" are equivalent to "A | B | C", and finally "C | B | A" is equivalent to
> "A | B | C" (to support the latter, the implementation needs to sort
> variants in some arbitrary total order before assigning tag numbers).
>
> Furthermore, a way to bind variables to an "or" pattern is introduced to
> allow to convert "A | B | C" to "A | B" in the case that it holds an A or a
> B.
>
> This way, one can rewrite Option as a type alias like this:
> struct Some<T>(T);
> struct None;
>
> type Option<T> = None | Some<T>;
>
> Which is like the current Option, but also makes None and Some<T>
> first-class types.
>
> The current enum syntax can remain as syntax sugar for the above code.
>
> The only issue I see is what to do for code such as "let mut x = Some(3);
> x = None;": with this proposal, Some and None are separate unrelated types,
> so we either have this code emit an error, or x must be given the type
> "Some<int> | None" automatically, which however can lead to obscure error
> messages if one mistakenly attempts to assign a string to it causing the
> type to become "Some<int> | None | ~str" (i.e. the user might be told than
> a match is not exhaustive because it does not handle the "~str" case,
> rather than that they assigned a ~str to an Option-typed variable).
>
> It should be possible to allow this, and make the error-emitting code use
> heuristics to figure out whether it is more likely that the user assigned a
> value of the wrong type, or used an enum improperly (for example, by
> looking at whether the implicitly created enum type is ever written
> explicitly in the source, and whether the deduced structural enum type is
> being used in places that require a non-enum type).
>
> Alternatively, one can stipulate that only types that are structs, or that
> are structs marked "enum struct" or "case struct" or similar can become
> part of an inferred structural enum, but this seems unappealing.
>
> Note that some structural enums can change representations depending
> generic instantiation, since "T | int" becomes just "int" if T = int, while
> it is "~str | int" if T = ~str (and similar for "Some<T> | Some<int>"), but
> this should not be a problem.
>
>
> _______________________________________________
> Rust-dev mailing list
> Rust-dev@mozilla.org
> https://mail.mozilla.org/listinfo/rust-dev
>
>
_______________________________________________
Rust-dev mailing list
Rust-dev@mozilla.org
https://mail.mozilla.org/listinfo/rust-dev

Reply via email to