replace switch for mapping

EntangledQuanta via Digitalmars-d-learn digitalmars-d-learn at puremagic.com
Thu Aug 31 16:17:52 PDT 2017


Generally one has to use a switch to map dynamic components. 
Given a set X and Y one can form a switch to map X to Y:

switch(X)
{
    case x1 : y1; break;
    ....
    case x1 : y1;
}

Is there any easier way to do this where one simply specifies the 
set's rather than having to create a switch directly?

In my specific case, I have to map a two sets of types

A = {Ta1,...,Tan}
B = {Tb1,...,Tbm}

to a template function that takes two types

foo(Tak, Taj)

so, given an arbitrary (a,b) in AxB, it it maps to foo(F(a),G(b)).

Using switches would require n*m cases.

What I actually have is something like

enum X
{
    Float,
    Int,
    `Etc`
}

and X x, y;

and need to call foo!(x,y) but with x and y replaced by their 
correct D equivalent types.

e.g., if x = X.Float; y = X.Int; then I need to call 
foo!(float,int) rather than foo!(X.Float,x.Int).


This allows me to create a dynamic dispatcher at runtime and use 
a templated function rather than having to handle each type 
independently. One templated function rather than nxm regular 
functions for each type or a nxm switch.

Unfortunately, a complicating factor is that the enum's names do 
not directly correspond to the D types through some simple 
transformation(e.g., lowerCase). D doesn't seem to support 
attributes on enum members for some inane reason and using 
strings will complicate 
things[https://forum.dlang.org/post/nmgloo$bd1$1@digitalmars.com]. I think I could use a struct though to solve that.

So, given something like

struct A
{
    @("float") enum Float = 0,
    @("int") enum Int = 1,
}

struct B
{
    @("double") enum Double = 0,
    @("short") enum Short = 1,
}

foo(T1,T2)();

create a mapping that takes an A and B and maps AxB to foo that 
does something like the following internally.

fooDispatch(A a, B b)
{
     switch(a) // Actually needs to be over attributes
     {
         case "float" :
             switch(b) // Actually needs to be over attributes
             {
                case "double" : return foo!(float, double)();
             }
         ...
     }
}


or whatever. I could write a string mixin that generates the 
above code but I'm hoping I don't have to and some genius will 
find a simple way to do it quickly, efficiently, and performant.






More information about the Digitalmars-d-learn mailing list