Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Type enum in std.variant.Algebraic for final switches #9608

Open
dlangBugzillaToGithub opened this issue Jun 27, 2013 · 3 comments
Open

Type enum in std.variant.Algebraic for final switches #9608

dlangBugzillaToGithub opened this issue Jun 27, 2013 · 3 comments

Comments

@dlangBugzillaToGithub
Copy link

bearophile_hugs reported this on 2013-06-27T13:48:47Z

Transfered from https://issues.dlang.org/show_bug.cgi?id=10490

CC List

  • diggsey
  • justin

Description

This enhancement request is just an idea. Maybe better ideas can be found.

Given the definition of an Algebraic like this:

import std.variant;
struct Foo {}
void main() {
    alias T = Algebraic!(int, Foo);
}



I think it can be a good idea to generate automatically inside T an enum and a method like this:

enum Type { int_, Foo; }

@property Type theType() const { return ...; }

(Built-in types are keywords so they get a leading underscore.)


So an Algebraic can be used in a final switch:

import std.variant;
struct Foo {}
void main() {
    alias T = Algebraic!(int, Foo);
    auto t = T(5);
    final switch (t.theType) {
        case T.Type.int_:
            auto p = t.peek!int;
            break;
        case T.Type.Foo:
            auto p = t.peek!Foo;
            break;
    }
}


(Currently T.type is a TypeInfo, that can't be used in a final switch.)

This allows a poor man's safe pattern matching on an Algebraic.

An implementation of Issue 596 will allow to use a bit better pattern matching on an Algebraic.
@dlangBugzillaToGithub
Copy link
Author

diggsey commented on 2013-06-27T15:04:30Z

This is related to Issue 10127

Personally I like that syntax where you use the actual type name rather than putting an underscore in front - it means you can easily use any type, not just ones that can be named.

Algebraic could then have an alias to a particular instantiation of that TypeEnum template inside it rather than generating its own.

@dlangBugzillaToGithub
Copy link
Author

justin commented on 2015-04-17T18:39:29Z

I've been using this solution, perhaps it should be included in std.variant, though possibly with a better name:

----
import std.variant;
import std.traits : isInstanceOf;

/**
 * Calls the correct overload of Fun based on the runtime value of the Variant value.
 */
auto applyToAlgebraic(alias Fun, Value)(Value value)
	if (isInstanceOf!(VariantN, Value))  // Can we constrain to Algebraic only?
{
	foreach (T; Value.AllowedTypes) // unrolled at CT
		if (typeid(T) is value.type)
			return Fun(value.get!T);
	assert(0);
}
----

@dlangBugzillaToGithub
Copy link
Author

justin commented on 2015-04-17T21:17:22Z

Oops, that should use `value.peek!T`, not `value.get!T`

@LightBender LightBender removed the P4 label Dec 6, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

2 participants