c++ build a name to function table, functions have different signature












0















I want to know, if it is possible to build a name to function table in c++, something like map<string, function handle>. But




  1. those functions have different signatures. I can assume they have same return type as void.



  2. I was thinking define something like,



    struct ftable
    {
    std::string name;
    void (void* pfun)(); // this is only for one function signature
    };




But how to make it work for different types of function?



I asked a related question here. In that question, I try to store functions into some container, but I realize that I can not store function with placeholder (see following code). Is this possible with c++? Thanks!



template <typename F, typename ... Args>
std::function<void()> MapFun (F const & f, Args const & ... args)
{ return [=]{ f(args...); }; }

void userFun1 (int i1, int i2)
{ std::cout << "uf1, " << i1 << ", " << i2 << std::endl; }

int main ()
{
auto l1 = MapFun(userFun1, 1, 2);
std::unordered_map<std::string, std::function<void()>> func_map;
func_map["userFun1"] = std::bind(l1); // this is okay;
//func_map["userFun1"] = std::bind(userFun1, std::placeholders::_1, std::placeholders::_2); // this is wrong;
//auto lll1 = MapFun(userFun1, std::placeholders::_1,std::placeholders::_2); // also wrong.
}


UPDATE: What I want is like plugin development. I have a server and a client. I can write my function on client, and build it as a shared library, then send that shared library to server as well as a signal telling server to load it. I hope server program can load function with different signatures from shared library without restart or rebuild. Is this possible, or I have to fix the signature and restrict all shared functions with that?










share|improve this question




















  • 5





    Why do you think you need this? Sounds like and XY problem to me. What is the underlying problem you are trying to solve?

    – super
    Nov 15 '18 at 5:11






  • 7





    After you retrieve a function from the map, how will you know what its signature is?

    – Raymond Chen
    Nov 15 '18 at 5:13











  • @RaymondChen I think you are right. C++ is a language needs to know type at compilation.

    – J.Yang
    Nov 15 '18 at 14:30











  • I have updated my question, @super, thanks for your comment

    – J.Yang
    Nov 15 '18 at 14:31











  • If you know the signature at compile time (e.g. "The item named bob is always a void(*)(int,int)") then you can cast a plain function pointer to void(*)() for storage, then cast it to void(*)(int,int) after retrieving. Function pointers of different signature can be interconverted without loss of fidelity, but you have to cast back to the original type before using them to call the function. If you cast to the wrong signature and then try to call the function, the result is undefined (i.e., "bad").

    – Raymond Chen
    Nov 15 '18 at 15:37


















0















I want to know, if it is possible to build a name to function table in c++, something like map<string, function handle>. But




  1. those functions have different signatures. I can assume they have same return type as void.



  2. I was thinking define something like,



    struct ftable
    {
    std::string name;
    void (void* pfun)(); // this is only for one function signature
    };




But how to make it work for different types of function?



I asked a related question here. In that question, I try to store functions into some container, but I realize that I can not store function with placeholder (see following code). Is this possible with c++? Thanks!



template <typename F, typename ... Args>
std::function<void()> MapFun (F const & f, Args const & ... args)
{ return [=]{ f(args...); }; }

void userFun1 (int i1, int i2)
{ std::cout << "uf1, " << i1 << ", " << i2 << std::endl; }

int main ()
{
auto l1 = MapFun(userFun1, 1, 2);
std::unordered_map<std::string, std::function<void()>> func_map;
func_map["userFun1"] = std::bind(l1); // this is okay;
//func_map["userFun1"] = std::bind(userFun1, std::placeholders::_1, std::placeholders::_2); // this is wrong;
//auto lll1 = MapFun(userFun1, std::placeholders::_1,std::placeholders::_2); // also wrong.
}


UPDATE: What I want is like plugin development. I have a server and a client. I can write my function on client, and build it as a shared library, then send that shared library to server as well as a signal telling server to load it. I hope server program can load function with different signatures from shared library without restart or rebuild. Is this possible, or I have to fix the signature and restrict all shared functions with that?










share|improve this question




















  • 5





    Why do you think you need this? Sounds like and XY problem to me. What is the underlying problem you are trying to solve?

    – super
    Nov 15 '18 at 5:11






  • 7





    After you retrieve a function from the map, how will you know what its signature is?

    – Raymond Chen
    Nov 15 '18 at 5:13











  • @RaymondChen I think you are right. C++ is a language needs to know type at compilation.

    – J.Yang
    Nov 15 '18 at 14:30











  • I have updated my question, @super, thanks for your comment

    – J.Yang
    Nov 15 '18 at 14:31











  • If you know the signature at compile time (e.g. "The item named bob is always a void(*)(int,int)") then you can cast a plain function pointer to void(*)() for storage, then cast it to void(*)(int,int) after retrieving. Function pointers of different signature can be interconverted without loss of fidelity, but you have to cast back to the original type before using them to call the function. If you cast to the wrong signature and then try to call the function, the result is undefined (i.e., "bad").

    – Raymond Chen
    Nov 15 '18 at 15:37
















0












0








0


1






I want to know, if it is possible to build a name to function table in c++, something like map<string, function handle>. But




  1. those functions have different signatures. I can assume they have same return type as void.



  2. I was thinking define something like,



    struct ftable
    {
    std::string name;
    void (void* pfun)(); // this is only for one function signature
    };




But how to make it work for different types of function?



I asked a related question here. In that question, I try to store functions into some container, but I realize that I can not store function with placeholder (see following code). Is this possible with c++? Thanks!



template <typename F, typename ... Args>
std::function<void()> MapFun (F const & f, Args const & ... args)
{ return [=]{ f(args...); }; }

void userFun1 (int i1, int i2)
{ std::cout << "uf1, " << i1 << ", " << i2 << std::endl; }

int main ()
{
auto l1 = MapFun(userFun1, 1, 2);
std::unordered_map<std::string, std::function<void()>> func_map;
func_map["userFun1"] = std::bind(l1); // this is okay;
//func_map["userFun1"] = std::bind(userFun1, std::placeholders::_1, std::placeholders::_2); // this is wrong;
//auto lll1 = MapFun(userFun1, std::placeholders::_1,std::placeholders::_2); // also wrong.
}


UPDATE: What I want is like plugin development. I have a server and a client. I can write my function on client, and build it as a shared library, then send that shared library to server as well as a signal telling server to load it. I hope server program can load function with different signatures from shared library without restart or rebuild. Is this possible, or I have to fix the signature and restrict all shared functions with that?










share|improve this question
















I want to know, if it is possible to build a name to function table in c++, something like map<string, function handle>. But




  1. those functions have different signatures. I can assume they have same return type as void.



  2. I was thinking define something like,



    struct ftable
    {
    std::string name;
    void (void* pfun)(); // this is only for one function signature
    };




But how to make it work for different types of function?



I asked a related question here. In that question, I try to store functions into some container, but I realize that I can not store function with placeholder (see following code). Is this possible with c++? Thanks!



template <typename F, typename ... Args>
std::function<void()> MapFun (F const & f, Args const & ... args)
{ return [=]{ f(args...); }; }

void userFun1 (int i1, int i2)
{ std::cout << "uf1, " << i1 << ", " << i2 << std::endl; }

int main ()
{
auto l1 = MapFun(userFun1, 1, 2);
std::unordered_map<std::string, std::function<void()>> func_map;
func_map["userFun1"] = std::bind(l1); // this is okay;
//func_map["userFun1"] = std::bind(userFun1, std::placeholders::_1, std::placeholders::_2); // this is wrong;
//auto lll1 = MapFun(userFun1, std::placeholders::_1,std::placeholders::_2); // also wrong.
}


UPDATE: What I want is like plugin development. I have a server and a client. I can write my function on client, and build it as a shared library, then send that shared library to server as well as a signal telling server to load it. I hope server program can load function with different signatures from shared library without restart or rebuild. Is this possible, or I have to fix the signature and restrict all shared functions with that?







c++ function c++11 c++17






share|improve this question















share|improve this question













share|improve this question




share|improve this question








edited Nov 15 '18 at 14:28







J.Yang

















asked Nov 15 '18 at 5:04









J.YangJ.Yang

246




246








  • 5





    Why do you think you need this? Sounds like and XY problem to me. What is the underlying problem you are trying to solve?

    – super
    Nov 15 '18 at 5:11






  • 7





    After you retrieve a function from the map, how will you know what its signature is?

    – Raymond Chen
    Nov 15 '18 at 5:13











  • @RaymondChen I think you are right. C++ is a language needs to know type at compilation.

    – J.Yang
    Nov 15 '18 at 14:30











  • I have updated my question, @super, thanks for your comment

    – J.Yang
    Nov 15 '18 at 14:31











  • If you know the signature at compile time (e.g. "The item named bob is always a void(*)(int,int)") then you can cast a plain function pointer to void(*)() for storage, then cast it to void(*)(int,int) after retrieving. Function pointers of different signature can be interconverted without loss of fidelity, but you have to cast back to the original type before using them to call the function. If you cast to the wrong signature and then try to call the function, the result is undefined (i.e., "bad").

    – Raymond Chen
    Nov 15 '18 at 15:37
















  • 5





    Why do you think you need this? Sounds like and XY problem to me. What is the underlying problem you are trying to solve?

    – super
    Nov 15 '18 at 5:11






  • 7





    After you retrieve a function from the map, how will you know what its signature is?

    – Raymond Chen
    Nov 15 '18 at 5:13











  • @RaymondChen I think you are right. C++ is a language needs to know type at compilation.

    – J.Yang
    Nov 15 '18 at 14:30











  • I have updated my question, @super, thanks for your comment

    – J.Yang
    Nov 15 '18 at 14:31











  • If you know the signature at compile time (e.g. "The item named bob is always a void(*)(int,int)") then you can cast a plain function pointer to void(*)() for storage, then cast it to void(*)(int,int) after retrieving. Function pointers of different signature can be interconverted without loss of fidelity, but you have to cast back to the original type before using them to call the function. If you cast to the wrong signature and then try to call the function, the result is undefined (i.e., "bad").

    – Raymond Chen
    Nov 15 '18 at 15:37










5




5





Why do you think you need this? Sounds like and XY problem to me. What is the underlying problem you are trying to solve?

– super
Nov 15 '18 at 5:11





Why do you think you need this? Sounds like and XY problem to me. What is the underlying problem you are trying to solve?

– super
Nov 15 '18 at 5:11




7




7





After you retrieve a function from the map, how will you know what its signature is?

– Raymond Chen
Nov 15 '18 at 5:13





After you retrieve a function from the map, how will you know what its signature is?

– Raymond Chen
Nov 15 '18 at 5:13













@RaymondChen I think you are right. C++ is a language needs to know type at compilation.

– J.Yang
Nov 15 '18 at 14:30





@RaymondChen I think you are right. C++ is a language needs to know type at compilation.

– J.Yang
Nov 15 '18 at 14:30













I have updated my question, @super, thanks for your comment

– J.Yang
Nov 15 '18 at 14:31





I have updated my question, @super, thanks for your comment

– J.Yang
Nov 15 '18 at 14:31













If you know the signature at compile time (e.g. "The item named bob is always a void(*)(int,int)") then you can cast a plain function pointer to void(*)() for storage, then cast it to void(*)(int,int) after retrieving. Function pointers of different signature can be interconverted without loss of fidelity, but you have to cast back to the original type before using them to call the function. If you cast to the wrong signature and then try to call the function, the result is undefined (i.e., "bad").

– Raymond Chen
Nov 15 '18 at 15:37







If you know the signature at compile time (e.g. "The item named bob is always a void(*)(int,int)") then you can cast a plain function pointer to void(*)() for storage, then cast it to void(*)(int,int) after retrieving. Function pointers of different signature can be interconverted without loss of fidelity, but you have to cast back to the original type before using them to call the function. If you cast to the wrong signature and then try to call the function, the result is undefined (i.e., "bad").

– Raymond Chen
Nov 15 '18 at 15:37














2 Answers
2






active

oldest

votes


















0














It is possible but at some point you will need to know the return and parameter types.



You can use a type-erasure class to hide the return/parameter types and then store the type-erasure class. A naive implementation like this would suffice,



#include <iostream>
#include <functional>
#include <unordered_map>

class MyLambda {

public:

MyLambda() = default;

virtual ~MyLambda() = default;

};

template <typename T>
class HiddenLambda : public MyLambda {
static_assert(std::integral_constant<T, false>::value, "Template parameter needs to be of function type.");
};

template <typename Ret, typename... Args>
class HiddenLambda<Ret(Args...)> : public MyLambda {

public:

HiddenLambda(std::function<Ret(Args...)> _fun) : fun_(_fun) { }

Ret operator() (Args... args) {return fun_(args...);}

private:

std::function<Ret(Args...)> fun_;
};

int main() {

std::unordered_map<std::string, std::shared_ptr<MyLambda>> my_lambdas;

my_lambdas.insert(std::make_pair("fun1", std::shared_ptr<MyLambda>(
new HiddenLambda<size_t(std::string)>(
(std::string s) { return s.size(); } // <- lambda you want to store
)
)
));

my_lambdas.insert(std::make_pair("fun2", std::shared_ptr<MyLambda>(
new HiddenLambda<int(int)>(
(int x) { return x * 5; } // <- lambda you want to store
)
)
));

auto it = my_lambdas.find("fun1");

/* Get the function we want! */
std::shared_ptr<MyLambda> a_lam = it->second;

/* Need to know the types to actually use it though */
HiddenLambda<size_t(std::string)>& actual_lam = dynamic_cast<HiddenLambda<size_t(std::string)>&>(*a_lam);

std::cout << actual_lam("how long is this string?") << "n";
}


If this is what we really need to do, I suggest looking up various methods for type erasure.



I think the problem you are trying to solve probably has an easier solution. If you could give more details perhaps we could help?



EDIT



More relevant example to your provided code...



/* include above classes and includes */
void myfunc(int x, int y) {
std::cout << "uf1, " << x << ", " << y << std::endl;
}

int main() {
std::unordered_map<std::string, std::shared_ptr<MyLambda>> func_map;

func_map["userFun1"] = std::shared_ptr<MyLambda>(
new HiddenLambda<void(int, int)>( &myfunc ) // <- no args binded, notice the type = void(int,int)
);

func_map["userFun2"] = std::shared_ptr<MyLambda>(
new HiddenLambda<void(int)>( std::bind(myfunc, std::placeholders::_1, 5) ) // <- one args binded, notice the type = void(int)
);

func_map["userFun3"] = std::shared_ptr<MyLambda>(
new HiddenLambda<void()>( std::bind(myfunc, 1, 2)) // <- two args binded, notice the type = void()
);

/* we still need to know the type though,it will be either void(int, int), void(int) or void() */
HiddenLambda<void(int)>& actual_lam = dynamic_cast<HiddenLambda<void(int)>&>(*func_map["userFun2"]);

actual_lam(4);

}


EDIT V2



This is more of a guess then anything. I am not sure if you should do this (well definitely not outside of some interesting experimentation) or if it will even work. Here is a possible way if the amount different arguments for different functions is known and finite. This would require a technique called Library Interposing, which I do not know much about.



Firstly in the main program you define this enum and a factory function. The enum will describe every possible parameter range.



enum Types { kVOID, kINT_INT }; // <- verbosely define all the possible ones you would use 

std::pair<Types, std::shared_ptr<MyLambda>> Factory(){
return
{
kVOID, /* <- some sensible default */
std::shared_ptr<MyLambda>(
new HiddenLambda<void()>( {} )
)
};
}


The shared library will have to provide an overriden factory method. Here is where I think you need the interposer to do so.



std::pair<Types, std::shared_ptr<MyLambda>> Factory(){
return
{
kVOID_INT_INT,
std::shared_ptr<MyLambda>(
new HiddenLambda<void(int, int)>( (int x, int y){ std::cout << (x + y);} )
)
};
}


Then the main method would look like:



int main() {

std::unordered_map<std::string, std::pair<Types, std::shared_ptr<MyLambda>>> func_map;

func_map.insert({"fun1", Factory()});

auto it = func_map.find("fun1");

/* always need to be able to deduce they type */
if (it->second.first == kVOID) {

CallHidden(*it->second.second);
}

else if (it->second.first == kINT_INT) {

CallHidden<int, int>(*it->second.second, 3, 4);

} else {

/* other ones you have statically typed */

}
}





share|improve this answer


























  • The static_assert only covers view data types (what about floating point types? classes/structs?). Better: Just do not implement the template!

    – Aconcagua
    Nov 15 '18 at 6:52











  • Thanks for your answer. But it still need to know the type when get the function handle out from the map. It has the same limitation like using std::vector<std::any>. I have updated my question, do you have any other suggestion?

    – J.Yang
    Nov 15 '18 at 14:40













  • @J.Yang You always need to know the signature. At some point in your code you will need to give arguments to the function, at that point you need to know the types of all the arguments. I have added an edit that may help.

    – Bar Stool
    Nov 16 '18 at 7:08











  • @J.Yang Please let me know if you get it working, I am interested to know what you end up doing. It you are satisfied with this answer, please consider accepting it.

    – Bar Stool
    Nov 16 '18 at 7:38











  • @BarStool Thank you for your patient. I need think about your EDIT V2. If this does not work, I think I will fix the signature for the shared function. So it will accept multiple vectors. If I want send a few int inputs, I have to put them all in one vector<int>, and take them out at the beginning of the function.

    – J.Yang
    Nov 17 '18 at 0:13



















0














If at time of creating object of std::function<void()>, you know function signature then you may be able to do like below.



#include <iostream>
#include <functional>
#include <unordered_map>

void userFun1 (int i1, int i2)
{
std::cout << "uf1, " << i1 << ", " << i2 << std::endl;
}


int main()
{
std::unordered_map<std::string, std::function<void()>> func_map;
func_map["userFun1"] = std::bind(userFun1,1,2);
func_map["userFun1"]();
int i1{2},i2{3};
func_map["userFun1.1"] = std::bind(userFun1,std::ref(i1),std::ref(i2));
func_map["userFun1.1"]();
i1 = 3;
i2 = 4;
func_map["userFun1.1"]();
return 0;
}


Live Code






share|improve this answer
























  • Thanks for your answer. That std::ref sounds like the tricky. I have updated my question, do you think this can be a workaround?

    – J.Yang
    Nov 15 '18 at 14:37











  • @J.Yang For your update,I don't think that may be possible. For any plugin system, there is fixed set of function call OR API which are know to both plugin loader and plugin it self. In your case you can create wrapper of your client code which know what are signature of client function and what are value need to pass to client function and call this wrapper function from your server code. Hope this will help!

    – Manthan Tilva
    Nov 16 '18 at 5:23













Your Answer






StackExchange.ifUsing("editor", function () {
StackExchange.using("externalEditor", function () {
StackExchange.using("snippets", function () {
StackExchange.snippets.init();
});
});
}, "code-snippets");

StackExchange.ready(function() {
var channelOptions = {
tags: "".split(" "),
id: "1"
};
initTagRenderer("".split(" "), "".split(" "), channelOptions);

StackExchange.using("externalEditor", function() {
// Have to fire editor after snippets, if snippets enabled
if (StackExchange.settings.snippets.snippetsEnabled) {
StackExchange.using("snippets", function() {
createEditor();
});
}
else {
createEditor();
}
});

function createEditor() {
StackExchange.prepareEditor({
heartbeatType: 'answer',
autoActivateHeartbeat: false,
convertImagesToLinks: true,
noModals: true,
showLowRepImageUploadWarning: true,
reputationToPostImages: 10,
bindNavPrevention: true,
postfix: "",
imageUploader: {
brandingHtml: "Powered by u003ca class="icon-imgur-white" href="https://imgur.com/"u003eu003c/au003e",
contentPolicyHtml: "User contributions licensed under u003ca href="https://creativecommons.org/licenses/by-sa/3.0/"u003ecc by-sa 3.0 with attribution requiredu003c/au003e u003ca href="https://stackoverflow.com/legal/content-policy"u003e(content policy)u003c/au003e",
allowUrls: true
},
onDemand: true,
discardSelector: ".discard-answer"
,immediatelyShowMarkdownHelp:true
});


}
});














draft saved

draft discarded


















StackExchange.ready(
function () {
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53312744%2fc-build-a-name-to-function-table-functions-have-different-signature%23new-answer', 'question_page');
}
);

Post as a guest















Required, but never shown

























2 Answers
2






active

oldest

votes








2 Answers
2






active

oldest

votes









active

oldest

votes






active

oldest

votes









0














It is possible but at some point you will need to know the return and parameter types.



You can use a type-erasure class to hide the return/parameter types and then store the type-erasure class. A naive implementation like this would suffice,



#include <iostream>
#include <functional>
#include <unordered_map>

class MyLambda {

public:

MyLambda() = default;

virtual ~MyLambda() = default;

};

template <typename T>
class HiddenLambda : public MyLambda {
static_assert(std::integral_constant<T, false>::value, "Template parameter needs to be of function type.");
};

template <typename Ret, typename... Args>
class HiddenLambda<Ret(Args...)> : public MyLambda {

public:

HiddenLambda(std::function<Ret(Args...)> _fun) : fun_(_fun) { }

Ret operator() (Args... args) {return fun_(args...);}

private:

std::function<Ret(Args...)> fun_;
};

int main() {

std::unordered_map<std::string, std::shared_ptr<MyLambda>> my_lambdas;

my_lambdas.insert(std::make_pair("fun1", std::shared_ptr<MyLambda>(
new HiddenLambda<size_t(std::string)>(
(std::string s) { return s.size(); } // <- lambda you want to store
)
)
));

my_lambdas.insert(std::make_pair("fun2", std::shared_ptr<MyLambda>(
new HiddenLambda<int(int)>(
(int x) { return x * 5; } // <- lambda you want to store
)
)
));

auto it = my_lambdas.find("fun1");

/* Get the function we want! */
std::shared_ptr<MyLambda> a_lam = it->second;

/* Need to know the types to actually use it though */
HiddenLambda<size_t(std::string)>& actual_lam = dynamic_cast<HiddenLambda<size_t(std::string)>&>(*a_lam);

std::cout << actual_lam("how long is this string?") << "n";
}


If this is what we really need to do, I suggest looking up various methods for type erasure.



I think the problem you are trying to solve probably has an easier solution. If you could give more details perhaps we could help?



EDIT



More relevant example to your provided code...



/* include above classes and includes */
void myfunc(int x, int y) {
std::cout << "uf1, " << x << ", " << y << std::endl;
}

int main() {
std::unordered_map<std::string, std::shared_ptr<MyLambda>> func_map;

func_map["userFun1"] = std::shared_ptr<MyLambda>(
new HiddenLambda<void(int, int)>( &myfunc ) // <- no args binded, notice the type = void(int,int)
);

func_map["userFun2"] = std::shared_ptr<MyLambda>(
new HiddenLambda<void(int)>( std::bind(myfunc, std::placeholders::_1, 5) ) // <- one args binded, notice the type = void(int)
);

func_map["userFun3"] = std::shared_ptr<MyLambda>(
new HiddenLambda<void()>( std::bind(myfunc, 1, 2)) // <- two args binded, notice the type = void()
);

/* we still need to know the type though,it will be either void(int, int), void(int) or void() */
HiddenLambda<void(int)>& actual_lam = dynamic_cast<HiddenLambda<void(int)>&>(*func_map["userFun2"]);

actual_lam(4);

}


EDIT V2



This is more of a guess then anything. I am not sure if you should do this (well definitely not outside of some interesting experimentation) or if it will even work. Here is a possible way if the amount different arguments for different functions is known and finite. This would require a technique called Library Interposing, which I do not know much about.



Firstly in the main program you define this enum and a factory function. The enum will describe every possible parameter range.



enum Types { kVOID, kINT_INT }; // <- verbosely define all the possible ones you would use 

std::pair<Types, std::shared_ptr<MyLambda>> Factory(){
return
{
kVOID, /* <- some sensible default */
std::shared_ptr<MyLambda>(
new HiddenLambda<void()>( {} )
)
};
}


The shared library will have to provide an overriden factory method. Here is where I think you need the interposer to do so.



std::pair<Types, std::shared_ptr<MyLambda>> Factory(){
return
{
kVOID_INT_INT,
std::shared_ptr<MyLambda>(
new HiddenLambda<void(int, int)>( (int x, int y){ std::cout << (x + y);} )
)
};
}


Then the main method would look like:



int main() {

std::unordered_map<std::string, std::pair<Types, std::shared_ptr<MyLambda>>> func_map;

func_map.insert({"fun1", Factory()});

auto it = func_map.find("fun1");

/* always need to be able to deduce they type */
if (it->second.first == kVOID) {

CallHidden(*it->second.second);
}

else if (it->second.first == kINT_INT) {

CallHidden<int, int>(*it->second.second, 3, 4);

} else {

/* other ones you have statically typed */

}
}





share|improve this answer


























  • The static_assert only covers view data types (what about floating point types? classes/structs?). Better: Just do not implement the template!

    – Aconcagua
    Nov 15 '18 at 6:52











  • Thanks for your answer. But it still need to know the type when get the function handle out from the map. It has the same limitation like using std::vector<std::any>. I have updated my question, do you have any other suggestion?

    – J.Yang
    Nov 15 '18 at 14:40













  • @J.Yang You always need to know the signature. At some point in your code you will need to give arguments to the function, at that point you need to know the types of all the arguments. I have added an edit that may help.

    – Bar Stool
    Nov 16 '18 at 7:08











  • @J.Yang Please let me know if you get it working, I am interested to know what you end up doing. It you are satisfied with this answer, please consider accepting it.

    – Bar Stool
    Nov 16 '18 at 7:38











  • @BarStool Thank you for your patient. I need think about your EDIT V2. If this does not work, I think I will fix the signature for the shared function. So it will accept multiple vectors. If I want send a few int inputs, I have to put them all in one vector<int>, and take them out at the beginning of the function.

    – J.Yang
    Nov 17 '18 at 0:13
















0














It is possible but at some point you will need to know the return and parameter types.



You can use a type-erasure class to hide the return/parameter types and then store the type-erasure class. A naive implementation like this would suffice,



#include <iostream>
#include <functional>
#include <unordered_map>

class MyLambda {

public:

MyLambda() = default;

virtual ~MyLambda() = default;

};

template <typename T>
class HiddenLambda : public MyLambda {
static_assert(std::integral_constant<T, false>::value, "Template parameter needs to be of function type.");
};

template <typename Ret, typename... Args>
class HiddenLambda<Ret(Args...)> : public MyLambda {

public:

HiddenLambda(std::function<Ret(Args...)> _fun) : fun_(_fun) { }

Ret operator() (Args... args) {return fun_(args...);}

private:

std::function<Ret(Args...)> fun_;
};

int main() {

std::unordered_map<std::string, std::shared_ptr<MyLambda>> my_lambdas;

my_lambdas.insert(std::make_pair("fun1", std::shared_ptr<MyLambda>(
new HiddenLambda<size_t(std::string)>(
(std::string s) { return s.size(); } // <- lambda you want to store
)
)
));

my_lambdas.insert(std::make_pair("fun2", std::shared_ptr<MyLambda>(
new HiddenLambda<int(int)>(
(int x) { return x * 5; } // <- lambda you want to store
)
)
));

auto it = my_lambdas.find("fun1");

/* Get the function we want! */
std::shared_ptr<MyLambda> a_lam = it->second;

/* Need to know the types to actually use it though */
HiddenLambda<size_t(std::string)>& actual_lam = dynamic_cast<HiddenLambda<size_t(std::string)>&>(*a_lam);

std::cout << actual_lam("how long is this string?") << "n";
}


If this is what we really need to do, I suggest looking up various methods for type erasure.



I think the problem you are trying to solve probably has an easier solution. If you could give more details perhaps we could help?



EDIT



More relevant example to your provided code...



/* include above classes and includes */
void myfunc(int x, int y) {
std::cout << "uf1, " << x << ", " << y << std::endl;
}

int main() {
std::unordered_map<std::string, std::shared_ptr<MyLambda>> func_map;

func_map["userFun1"] = std::shared_ptr<MyLambda>(
new HiddenLambda<void(int, int)>( &myfunc ) // <- no args binded, notice the type = void(int,int)
);

func_map["userFun2"] = std::shared_ptr<MyLambda>(
new HiddenLambda<void(int)>( std::bind(myfunc, std::placeholders::_1, 5) ) // <- one args binded, notice the type = void(int)
);

func_map["userFun3"] = std::shared_ptr<MyLambda>(
new HiddenLambda<void()>( std::bind(myfunc, 1, 2)) // <- two args binded, notice the type = void()
);

/* we still need to know the type though,it will be either void(int, int), void(int) or void() */
HiddenLambda<void(int)>& actual_lam = dynamic_cast<HiddenLambda<void(int)>&>(*func_map["userFun2"]);

actual_lam(4);

}


EDIT V2



This is more of a guess then anything. I am not sure if you should do this (well definitely not outside of some interesting experimentation) or if it will even work. Here is a possible way if the amount different arguments for different functions is known and finite. This would require a technique called Library Interposing, which I do not know much about.



Firstly in the main program you define this enum and a factory function. The enum will describe every possible parameter range.



enum Types { kVOID, kINT_INT }; // <- verbosely define all the possible ones you would use 

std::pair<Types, std::shared_ptr<MyLambda>> Factory(){
return
{
kVOID, /* <- some sensible default */
std::shared_ptr<MyLambda>(
new HiddenLambda<void()>( {} )
)
};
}


The shared library will have to provide an overriden factory method. Here is where I think you need the interposer to do so.



std::pair<Types, std::shared_ptr<MyLambda>> Factory(){
return
{
kVOID_INT_INT,
std::shared_ptr<MyLambda>(
new HiddenLambda<void(int, int)>( (int x, int y){ std::cout << (x + y);} )
)
};
}


Then the main method would look like:



int main() {

std::unordered_map<std::string, std::pair<Types, std::shared_ptr<MyLambda>>> func_map;

func_map.insert({"fun1", Factory()});

auto it = func_map.find("fun1");

/* always need to be able to deduce they type */
if (it->second.first == kVOID) {

CallHidden(*it->second.second);
}

else if (it->second.first == kINT_INT) {

CallHidden<int, int>(*it->second.second, 3, 4);

} else {

/* other ones you have statically typed */

}
}





share|improve this answer


























  • The static_assert only covers view data types (what about floating point types? classes/structs?). Better: Just do not implement the template!

    – Aconcagua
    Nov 15 '18 at 6:52











  • Thanks for your answer. But it still need to know the type when get the function handle out from the map. It has the same limitation like using std::vector<std::any>. I have updated my question, do you have any other suggestion?

    – J.Yang
    Nov 15 '18 at 14:40













  • @J.Yang You always need to know the signature. At some point in your code you will need to give arguments to the function, at that point you need to know the types of all the arguments. I have added an edit that may help.

    – Bar Stool
    Nov 16 '18 at 7:08











  • @J.Yang Please let me know if you get it working, I am interested to know what you end up doing. It you are satisfied with this answer, please consider accepting it.

    – Bar Stool
    Nov 16 '18 at 7:38











  • @BarStool Thank you for your patient. I need think about your EDIT V2. If this does not work, I think I will fix the signature for the shared function. So it will accept multiple vectors. If I want send a few int inputs, I have to put them all in one vector<int>, and take them out at the beginning of the function.

    – J.Yang
    Nov 17 '18 at 0:13














0












0








0







It is possible but at some point you will need to know the return and parameter types.



You can use a type-erasure class to hide the return/parameter types and then store the type-erasure class. A naive implementation like this would suffice,



#include <iostream>
#include <functional>
#include <unordered_map>

class MyLambda {

public:

MyLambda() = default;

virtual ~MyLambda() = default;

};

template <typename T>
class HiddenLambda : public MyLambda {
static_assert(std::integral_constant<T, false>::value, "Template parameter needs to be of function type.");
};

template <typename Ret, typename... Args>
class HiddenLambda<Ret(Args...)> : public MyLambda {

public:

HiddenLambda(std::function<Ret(Args...)> _fun) : fun_(_fun) { }

Ret operator() (Args... args) {return fun_(args...);}

private:

std::function<Ret(Args...)> fun_;
};

int main() {

std::unordered_map<std::string, std::shared_ptr<MyLambda>> my_lambdas;

my_lambdas.insert(std::make_pair("fun1", std::shared_ptr<MyLambda>(
new HiddenLambda<size_t(std::string)>(
(std::string s) { return s.size(); } // <- lambda you want to store
)
)
));

my_lambdas.insert(std::make_pair("fun2", std::shared_ptr<MyLambda>(
new HiddenLambda<int(int)>(
(int x) { return x * 5; } // <- lambda you want to store
)
)
));

auto it = my_lambdas.find("fun1");

/* Get the function we want! */
std::shared_ptr<MyLambda> a_lam = it->second;

/* Need to know the types to actually use it though */
HiddenLambda<size_t(std::string)>& actual_lam = dynamic_cast<HiddenLambda<size_t(std::string)>&>(*a_lam);

std::cout << actual_lam("how long is this string?") << "n";
}


If this is what we really need to do, I suggest looking up various methods for type erasure.



I think the problem you are trying to solve probably has an easier solution. If you could give more details perhaps we could help?



EDIT



More relevant example to your provided code...



/* include above classes and includes */
void myfunc(int x, int y) {
std::cout << "uf1, " << x << ", " << y << std::endl;
}

int main() {
std::unordered_map<std::string, std::shared_ptr<MyLambda>> func_map;

func_map["userFun1"] = std::shared_ptr<MyLambda>(
new HiddenLambda<void(int, int)>( &myfunc ) // <- no args binded, notice the type = void(int,int)
);

func_map["userFun2"] = std::shared_ptr<MyLambda>(
new HiddenLambda<void(int)>( std::bind(myfunc, std::placeholders::_1, 5) ) // <- one args binded, notice the type = void(int)
);

func_map["userFun3"] = std::shared_ptr<MyLambda>(
new HiddenLambda<void()>( std::bind(myfunc, 1, 2)) // <- two args binded, notice the type = void()
);

/* we still need to know the type though,it will be either void(int, int), void(int) or void() */
HiddenLambda<void(int)>& actual_lam = dynamic_cast<HiddenLambda<void(int)>&>(*func_map["userFun2"]);

actual_lam(4);

}


EDIT V2



This is more of a guess then anything. I am not sure if you should do this (well definitely not outside of some interesting experimentation) or if it will even work. Here is a possible way if the amount different arguments for different functions is known and finite. This would require a technique called Library Interposing, which I do not know much about.



Firstly in the main program you define this enum and a factory function. The enum will describe every possible parameter range.



enum Types { kVOID, kINT_INT }; // <- verbosely define all the possible ones you would use 

std::pair<Types, std::shared_ptr<MyLambda>> Factory(){
return
{
kVOID, /* <- some sensible default */
std::shared_ptr<MyLambda>(
new HiddenLambda<void()>( {} )
)
};
}


The shared library will have to provide an overriden factory method. Here is where I think you need the interposer to do so.



std::pair<Types, std::shared_ptr<MyLambda>> Factory(){
return
{
kVOID_INT_INT,
std::shared_ptr<MyLambda>(
new HiddenLambda<void(int, int)>( (int x, int y){ std::cout << (x + y);} )
)
};
}


Then the main method would look like:



int main() {

std::unordered_map<std::string, std::pair<Types, std::shared_ptr<MyLambda>>> func_map;

func_map.insert({"fun1", Factory()});

auto it = func_map.find("fun1");

/* always need to be able to deduce they type */
if (it->second.first == kVOID) {

CallHidden(*it->second.second);
}

else if (it->second.first == kINT_INT) {

CallHidden<int, int>(*it->second.second, 3, 4);

} else {

/* other ones you have statically typed */

}
}





share|improve this answer















It is possible but at some point you will need to know the return and parameter types.



You can use a type-erasure class to hide the return/parameter types and then store the type-erasure class. A naive implementation like this would suffice,



#include <iostream>
#include <functional>
#include <unordered_map>

class MyLambda {

public:

MyLambda() = default;

virtual ~MyLambda() = default;

};

template <typename T>
class HiddenLambda : public MyLambda {
static_assert(std::integral_constant<T, false>::value, "Template parameter needs to be of function type.");
};

template <typename Ret, typename... Args>
class HiddenLambda<Ret(Args...)> : public MyLambda {

public:

HiddenLambda(std::function<Ret(Args...)> _fun) : fun_(_fun) { }

Ret operator() (Args... args) {return fun_(args...);}

private:

std::function<Ret(Args...)> fun_;
};

int main() {

std::unordered_map<std::string, std::shared_ptr<MyLambda>> my_lambdas;

my_lambdas.insert(std::make_pair("fun1", std::shared_ptr<MyLambda>(
new HiddenLambda<size_t(std::string)>(
(std::string s) { return s.size(); } // <- lambda you want to store
)
)
));

my_lambdas.insert(std::make_pair("fun2", std::shared_ptr<MyLambda>(
new HiddenLambda<int(int)>(
(int x) { return x * 5; } // <- lambda you want to store
)
)
));

auto it = my_lambdas.find("fun1");

/* Get the function we want! */
std::shared_ptr<MyLambda> a_lam = it->second;

/* Need to know the types to actually use it though */
HiddenLambda<size_t(std::string)>& actual_lam = dynamic_cast<HiddenLambda<size_t(std::string)>&>(*a_lam);

std::cout << actual_lam("how long is this string?") << "n";
}


If this is what we really need to do, I suggest looking up various methods for type erasure.



I think the problem you are trying to solve probably has an easier solution. If you could give more details perhaps we could help?



EDIT



More relevant example to your provided code...



/* include above classes and includes */
void myfunc(int x, int y) {
std::cout << "uf1, " << x << ", " << y << std::endl;
}

int main() {
std::unordered_map<std::string, std::shared_ptr<MyLambda>> func_map;

func_map["userFun1"] = std::shared_ptr<MyLambda>(
new HiddenLambda<void(int, int)>( &myfunc ) // <- no args binded, notice the type = void(int,int)
);

func_map["userFun2"] = std::shared_ptr<MyLambda>(
new HiddenLambda<void(int)>( std::bind(myfunc, std::placeholders::_1, 5) ) // <- one args binded, notice the type = void(int)
);

func_map["userFun3"] = std::shared_ptr<MyLambda>(
new HiddenLambda<void()>( std::bind(myfunc, 1, 2)) // <- two args binded, notice the type = void()
);

/* we still need to know the type though,it will be either void(int, int), void(int) or void() */
HiddenLambda<void(int)>& actual_lam = dynamic_cast<HiddenLambda<void(int)>&>(*func_map["userFun2"]);

actual_lam(4);

}


EDIT V2



This is more of a guess then anything. I am not sure if you should do this (well definitely not outside of some interesting experimentation) or if it will even work. Here is a possible way if the amount different arguments for different functions is known and finite. This would require a technique called Library Interposing, which I do not know much about.



Firstly in the main program you define this enum and a factory function. The enum will describe every possible parameter range.



enum Types { kVOID, kINT_INT }; // <- verbosely define all the possible ones you would use 

std::pair<Types, std::shared_ptr<MyLambda>> Factory(){
return
{
kVOID, /* <- some sensible default */
std::shared_ptr<MyLambda>(
new HiddenLambda<void()>( {} )
)
};
}


The shared library will have to provide an overriden factory method. Here is where I think you need the interposer to do so.



std::pair<Types, std::shared_ptr<MyLambda>> Factory(){
return
{
kVOID_INT_INT,
std::shared_ptr<MyLambda>(
new HiddenLambda<void(int, int)>( (int x, int y){ std::cout << (x + y);} )
)
};
}


Then the main method would look like:



int main() {

std::unordered_map<std::string, std::pair<Types, std::shared_ptr<MyLambda>>> func_map;

func_map.insert({"fun1", Factory()});

auto it = func_map.find("fun1");

/* always need to be able to deduce they type */
if (it->second.first == kVOID) {

CallHidden(*it->second.second);
}

else if (it->second.first == kINT_INT) {

CallHidden<int, int>(*it->second.second, 3, 4);

} else {

/* other ones you have statically typed */

}
}






share|improve this answer














share|improve this answer



share|improve this answer








edited Nov 16 '18 at 7:35

























answered Nov 15 '18 at 6:17









Bar StoolBar Stool

1714




1714













  • The static_assert only covers view data types (what about floating point types? classes/structs?). Better: Just do not implement the template!

    – Aconcagua
    Nov 15 '18 at 6:52











  • Thanks for your answer. But it still need to know the type when get the function handle out from the map. It has the same limitation like using std::vector<std::any>. I have updated my question, do you have any other suggestion?

    – J.Yang
    Nov 15 '18 at 14:40













  • @J.Yang You always need to know the signature. At some point in your code you will need to give arguments to the function, at that point you need to know the types of all the arguments. I have added an edit that may help.

    – Bar Stool
    Nov 16 '18 at 7:08











  • @J.Yang Please let me know if you get it working, I am interested to know what you end up doing. It you are satisfied with this answer, please consider accepting it.

    – Bar Stool
    Nov 16 '18 at 7:38











  • @BarStool Thank you for your patient. I need think about your EDIT V2. If this does not work, I think I will fix the signature for the shared function. So it will accept multiple vectors. If I want send a few int inputs, I have to put them all in one vector<int>, and take them out at the beginning of the function.

    – J.Yang
    Nov 17 '18 at 0:13



















  • The static_assert only covers view data types (what about floating point types? classes/structs?). Better: Just do not implement the template!

    – Aconcagua
    Nov 15 '18 at 6:52











  • Thanks for your answer. But it still need to know the type when get the function handle out from the map. It has the same limitation like using std::vector<std::any>. I have updated my question, do you have any other suggestion?

    – J.Yang
    Nov 15 '18 at 14:40













  • @J.Yang You always need to know the signature. At some point in your code you will need to give arguments to the function, at that point you need to know the types of all the arguments. I have added an edit that may help.

    – Bar Stool
    Nov 16 '18 at 7:08











  • @J.Yang Please let me know if you get it working, I am interested to know what you end up doing. It you are satisfied with this answer, please consider accepting it.

    – Bar Stool
    Nov 16 '18 at 7:38











  • @BarStool Thank you for your patient. I need think about your EDIT V2. If this does not work, I think I will fix the signature for the shared function. So it will accept multiple vectors. If I want send a few int inputs, I have to put them all in one vector<int>, and take them out at the beginning of the function.

    – J.Yang
    Nov 17 '18 at 0:13

















The static_assert only covers view data types (what about floating point types? classes/structs?). Better: Just do not implement the template!

– Aconcagua
Nov 15 '18 at 6:52





The static_assert only covers view data types (what about floating point types? classes/structs?). Better: Just do not implement the template!

– Aconcagua
Nov 15 '18 at 6:52













Thanks for your answer. But it still need to know the type when get the function handle out from the map. It has the same limitation like using std::vector<std::any>. I have updated my question, do you have any other suggestion?

– J.Yang
Nov 15 '18 at 14:40







Thanks for your answer. But it still need to know the type when get the function handle out from the map. It has the same limitation like using std::vector<std::any>. I have updated my question, do you have any other suggestion?

– J.Yang
Nov 15 '18 at 14:40















@J.Yang You always need to know the signature. At some point in your code you will need to give arguments to the function, at that point you need to know the types of all the arguments. I have added an edit that may help.

– Bar Stool
Nov 16 '18 at 7:08





@J.Yang You always need to know the signature. At some point in your code you will need to give arguments to the function, at that point you need to know the types of all the arguments. I have added an edit that may help.

– Bar Stool
Nov 16 '18 at 7:08













@J.Yang Please let me know if you get it working, I am interested to know what you end up doing. It you are satisfied with this answer, please consider accepting it.

– Bar Stool
Nov 16 '18 at 7:38





@J.Yang Please let me know if you get it working, I am interested to know what you end up doing. It you are satisfied with this answer, please consider accepting it.

– Bar Stool
Nov 16 '18 at 7:38













@BarStool Thank you for your patient. I need think about your EDIT V2. If this does not work, I think I will fix the signature for the shared function. So it will accept multiple vectors. If I want send a few int inputs, I have to put them all in one vector<int>, and take them out at the beginning of the function.

– J.Yang
Nov 17 '18 at 0:13





@BarStool Thank you for your patient. I need think about your EDIT V2. If this does not work, I think I will fix the signature for the shared function. So it will accept multiple vectors. If I want send a few int inputs, I have to put them all in one vector<int>, and take them out at the beginning of the function.

– J.Yang
Nov 17 '18 at 0:13













0














If at time of creating object of std::function<void()>, you know function signature then you may be able to do like below.



#include <iostream>
#include <functional>
#include <unordered_map>

void userFun1 (int i1, int i2)
{
std::cout << "uf1, " << i1 << ", " << i2 << std::endl;
}


int main()
{
std::unordered_map<std::string, std::function<void()>> func_map;
func_map["userFun1"] = std::bind(userFun1,1,2);
func_map["userFun1"]();
int i1{2},i2{3};
func_map["userFun1.1"] = std::bind(userFun1,std::ref(i1),std::ref(i2));
func_map["userFun1.1"]();
i1 = 3;
i2 = 4;
func_map["userFun1.1"]();
return 0;
}


Live Code






share|improve this answer
























  • Thanks for your answer. That std::ref sounds like the tricky. I have updated my question, do you think this can be a workaround?

    – J.Yang
    Nov 15 '18 at 14:37











  • @J.Yang For your update,I don't think that may be possible. For any plugin system, there is fixed set of function call OR API which are know to both plugin loader and plugin it self. In your case you can create wrapper of your client code which know what are signature of client function and what are value need to pass to client function and call this wrapper function from your server code. Hope this will help!

    – Manthan Tilva
    Nov 16 '18 at 5:23


















0














If at time of creating object of std::function<void()>, you know function signature then you may be able to do like below.



#include <iostream>
#include <functional>
#include <unordered_map>

void userFun1 (int i1, int i2)
{
std::cout << "uf1, " << i1 << ", " << i2 << std::endl;
}


int main()
{
std::unordered_map<std::string, std::function<void()>> func_map;
func_map["userFun1"] = std::bind(userFun1,1,2);
func_map["userFun1"]();
int i1{2},i2{3};
func_map["userFun1.1"] = std::bind(userFun1,std::ref(i1),std::ref(i2));
func_map["userFun1.1"]();
i1 = 3;
i2 = 4;
func_map["userFun1.1"]();
return 0;
}


Live Code






share|improve this answer
























  • Thanks for your answer. That std::ref sounds like the tricky. I have updated my question, do you think this can be a workaround?

    – J.Yang
    Nov 15 '18 at 14:37











  • @J.Yang For your update,I don't think that may be possible. For any plugin system, there is fixed set of function call OR API which are know to both plugin loader and plugin it self. In your case you can create wrapper of your client code which know what are signature of client function and what are value need to pass to client function and call this wrapper function from your server code. Hope this will help!

    – Manthan Tilva
    Nov 16 '18 at 5:23
















0












0








0







If at time of creating object of std::function<void()>, you know function signature then you may be able to do like below.



#include <iostream>
#include <functional>
#include <unordered_map>

void userFun1 (int i1, int i2)
{
std::cout << "uf1, " << i1 << ", " << i2 << std::endl;
}


int main()
{
std::unordered_map<std::string, std::function<void()>> func_map;
func_map["userFun1"] = std::bind(userFun1,1,2);
func_map["userFun1"]();
int i1{2},i2{3};
func_map["userFun1.1"] = std::bind(userFun1,std::ref(i1),std::ref(i2));
func_map["userFun1.1"]();
i1 = 3;
i2 = 4;
func_map["userFun1.1"]();
return 0;
}


Live Code






share|improve this answer













If at time of creating object of std::function<void()>, you know function signature then you may be able to do like below.



#include <iostream>
#include <functional>
#include <unordered_map>

void userFun1 (int i1, int i2)
{
std::cout << "uf1, " << i1 << ", " << i2 << std::endl;
}


int main()
{
std::unordered_map<std::string, std::function<void()>> func_map;
func_map["userFun1"] = std::bind(userFun1,1,2);
func_map["userFun1"]();
int i1{2},i2{3};
func_map["userFun1.1"] = std::bind(userFun1,std::ref(i1),std::ref(i2));
func_map["userFun1.1"]();
i1 = 3;
i2 = 4;
func_map["userFun1.1"]();
return 0;
}


Live Code







share|improve this answer












share|improve this answer



share|improve this answer










answered Nov 15 '18 at 5:54









Manthan TilvaManthan Tilva

1,306823




1,306823













  • Thanks for your answer. That std::ref sounds like the tricky. I have updated my question, do you think this can be a workaround?

    – J.Yang
    Nov 15 '18 at 14:37











  • @J.Yang For your update,I don't think that may be possible. For any plugin system, there is fixed set of function call OR API which are know to both plugin loader and plugin it self. In your case you can create wrapper of your client code which know what are signature of client function and what are value need to pass to client function and call this wrapper function from your server code. Hope this will help!

    – Manthan Tilva
    Nov 16 '18 at 5:23





















  • Thanks for your answer. That std::ref sounds like the tricky. I have updated my question, do you think this can be a workaround?

    – J.Yang
    Nov 15 '18 at 14:37











  • @J.Yang For your update,I don't think that may be possible. For any plugin system, there is fixed set of function call OR API which are know to both plugin loader and plugin it self. In your case you can create wrapper of your client code which know what are signature of client function and what are value need to pass to client function and call this wrapper function from your server code. Hope this will help!

    – Manthan Tilva
    Nov 16 '18 at 5:23



















Thanks for your answer. That std::ref sounds like the tricky. I have updated my question, do you think this can be a workaround?

– J.Yang
Nov 15 '18 at 14:37





Thanks for your answer. That std::ref sounds like the tricky. I have updated my question, do you think this can be a workaround?

– J.Yang
Nov 15 '18 at 14:37













@J.Yang For your update,I don't think that may be possible. For any plugin system, there is fixed set of function call OR API which are know to both plugin loader and plugin it self. In your case you can create wrapper of your client code which know what are signature of client function and what are value need to pass to client function and call this wrapper function from your server code. Hope this will help!

– Manthan Tilva
Nov 16 '18 at 5:23







@J.Yang For your update,I don't think that may be possible. For any plugin system, there is fixed set of function call OR API which are know to both plugin loader and plugin it self. In your case you can create wrapper of your client code which know what are signature of client function and what are value need to pass to client function and call this wrapper function from your server code. Hope this will help!

– Manthan Tilva
Nov 16 '18 at 5:23




















draft saved

draft discarded




















































Thanks for contributing an answer to Stack Overflow!


  • Please be sure to answer the question. Provide details and share your research!

But avoid



  • Asking for help, clarification, or responding to other answers.

  • Making statements based on opinion; back them up with references or personal experience.


To learn more, see our tips on writing great answers.




draft saved


draft discarded














StackExchange.ready(
function () {
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53312744%2fc-build-a-name-to-function-table-functions-have-different-signature%23new-answer', 'question_page');
}
);

Post as a guest















Required, but never shown





















































Required, but never shown














Required, but never shown












Required, but never shown







Required, but never shown

































Required, but never shown














Required, but never shown












Required, but never shown







Required, but never shown







Popular posts from this blog

List item for chat from Array inside array React Native

Thiostrepton

Caerphilly