TaggedUnion is the low level tagged union functionality separated out from TaggedAlgebraic. Because it doesn't support transparent access of methods and operators of the contained value, it is able to provide a number of convenience features. On top of that, visit and tryVisit is now supported for pattern matching, analogous to the version for std.variant.Algebraic. This is the basic usage:

    union U {
        string caption;
        int height;
        int width;
    }
    alias Value = TaggedUnion!U;

    auto val = Value.caption("foo");
    assert(val.kind == Value.Kind.caption);
    assert(val.value!(Value.Kind.caption) == "foo");

    // shorthand syntax:
    assert(val.isCaption);
    assert(val.captionValue == "foo");

    // set a different type/kind
    val.setHeight(10);
    assert(val.isHeight && val.heightValue == 10);
    assert(!val.isWidth);

    assert(cast(short)val == 10);

    val.visit!(
        (int i) { assert(i == 10); }
        (string s) { assert(false); }
    );

    assert(val.visit!((v) => v.to!string) == "10");


Another addition is a new placeholder "This" type to enable defining self-referential types without having to write additional boilerplate code:

    union U {
        bool boolean;
        string text;
        float number;
        TaggedUnion!This[] array;
        TaggedUnion!This[string] object;
    }
    alias JsonValue = TaggedUnion!U;


The general advantages of TaggedUnion/TaggedAlgebraic over Algebraic result from its use of a numeric type tag instead of relying on runtime TypeInfo:

 - Allows compiler checked handling of all possible types/kinds using
   "final switch"
 - Enables inlining and function attribute inference (@safe, nothrow,
   @nogc)
 - Allows to use the same type with multiple tags to avoid the overhead
   of defining separate wrapper types
 - Behaves like a POD if only POD fields exist, is non-copyable if any
   contained type is non-copyable etc.


DUB: https://code.dlang.org/packages/taggedalgebraic
GitHub: https://github.com/s-ludwig/taggedalgebraic

Reply via email to