简体   繁体   中英

How to declare a std::map with enum as key and functions with varying signatures as values?

I suppose this is a very simple question to advanced C++ programmers, but I'm not one, so:

Using C++ 11, what's an elegant way to implement a std::map that uses a scoped enum as a key and takes mathematical functions that have varying signatures as values:

Simple example - could be any numeric type or any number of function args, but these are typical for my use case:

enum class FUNCS
    {
         DOUBLE_FUNC1, DOUBLE_FUNC2, INT_FUNC3, INT_FUNC4
    };

Some functions:

double f1( int a, int b, double d);
double f2( int a, int b, int c, int d);
int f3( int a, double d, int c, double e);
int f4( int a, double d, int c);

The functionality I seek is a std::map that works like this:

Initialize the map:

mMAP[FUNCS::DOUBLE_FUNC1]=f1;
mMAP[FUNCS::DOUBLE_FUNC2]=f2;
mMAP[FUNCS::INT_FUNC3]=f3;
mMAP[FUNCS::INT_FUNC4]=f4;

Use the map:

mMAP[FUNCS::DOUBLE_FUNC1](a,b,d);
mMAP[FUNCS::INT_FUNC3](a,d,c,e);

A compromise that would involve some type casting could use functions with varying arguments that all return double :

double f1( int a, int b, double d);
double f2( int a, int b, int c, int d);
double f3( int a, double d, int c, double e);
double f4( int a, double d, int c);

How can I can declare a map that will give me this functionality? I understand that I probably cannot map those functions directly to those keys - I will need some sort of abstraction/indirection to accomplish this goal, and I believe that using variadic functions/templates this can be accomplished, see Variadic arguments and Parameter pack , but I'm really not clear on how to do get this working.

Meanwhile I have implemented a cludgy solution using a function pointer type that takes a std::tuple containing a series of values of all possible types as an argument with references for the results, and then in each fuction mapped, I use the appropriate members of the tuple. UGLY!

My goal here is to send data from these various functions to a charting library which generates charts using data of type boost::any A GUI driven state machine will call the appropriate function through the map based on the enum value represented in the state machine, and generate a chart based on data from that function.

C++ is a statically typed language.

The only way you could do this would be to have all the functions use a common signature, for instance:

struct F1Data { double result; int a; int b; double d; };
struct F2Data { double result; int a, b, c, d; };
struct F3Data { int result; int a, b; double c; };
struct F4Data { int result; double a, b; int c; };

void f1(void* data);
void f2(void* data);
void f3(void* data);
void f4(void* data);

Then within each the functions, you can cast data to the right type and work on the values from there.

That's as close as you'll be able to get. You can mask it with libraries like tuple or any but it will always boil down to making a shared signature across all of the functions.

Since all functions have different signatures, it is not possible.

Since all functions have different types, you can't even use some kind of type erasure.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM