On Fri, Jan 9, 2015 at 9:52 AM, Eelis
On 2015-01-09 10:06, Antony Polukhin wrote:
I like the idea of `overload` more than the `match` idea.
I see many people prefer going through apply_visitor() with overload(). Coming from a functional programming perspective, this is kinda backwards.
I disagree completely. Please explain what you consider apply_visitor and overload to be "backwards"? All apply_visitor (or apply, or visit, or dispatch, or whatever the name) is is a high order function that takes a function object and invokes it with the trailing arguments upon transformation. There is nothing at all backwards about this from a functional programming perspective or any perspective.
What we need is sum types. C++ unions are sort of sum types, but they're crap, so variant<> is our C++ workaround.
While I agree that they are important, I would hardly call variant a "workaround" to not having language-level discriminated sum types, it's just a library implementation of that kind of sum type. In general, I am of the strong opinion that if a type can be efficiently implemented either as a library component or as a language feature, all else being equal, one should prefer it as a library component. In the case of something like variant, there are some benefits that can come from language support, but there are also some trade-offs with respect to a C++ implementation that, IMO, are not really a good idea to try to standardize at the core language level. Even if we had them, I have little doubt that there would still exist libraries that make alternative trade-offs anyway. However, somewhere along the line it was decided that variant<> was to be
accessed /by type/ (either through get<T>() or apply_visitor()), which means that variant
does not work well at all.
That's not why a variant has no repeated types. It is also not expected to be the only sum type abstraction is applicable to all situations.
This means variant<> fails to be the building block that sum types can/should be
Not true. It is trivial to build a generalized discriminated union on top
of variant. All you do is have the discriminated_union
Really, variant<> should have been index-based all along, so that you can just do get<0> and get<1> on a variant
(or a variant where A might be B) without losing information. Analogously, match(v, [](T){}, [](T){}) on such a variant would Just Work (again, without losing information), while apply_visitor() with overload() breaks down.
You seem to be not getting that discriminated_union and variant each are
used in different scenarios. One quick scenario for where you want a
variant is:
// Holds one of these collidable shapes.
variant