How to remove decltype(&MyClass::funct) part by extending the following type traits?
(Answer archived for future visitors; this solution requires C++17!)
You're really close!
The trick is auto
template arguments, and the fact that pointers-to-members can be used as template arguments, like so:
template <auto thing>
using class_t = get_class_t<decltype(thing)>;
int main()
{
class_t<&MyClass::funct> myObj;
myObj.funct();
}
Of course if you can write this then you already know the type so you'd just write MyClass
, so that's not very useful.
Sadly you won't be able to make it accept ptr
as a template argument, though; you're stuck with get_class_t
for that:
int main()
{
auto ptr = &MyClass::funct;
get_class_t<decltype(ptr)> myObj;
myObj.funct();
}
(live demo)
In the latter case, a nice type alias can help you a bit:
auto ptr = &MyClass::funct;
using ClassType = get_class_t<decltype(ptr)>;
ClassType myObj;
myObj.funct();
(live demo)
Personally I think this level of verbosity is pretty reasonable.
You can provide a function which will create required object. This is very simple to achieve:
template<typename T, typename ...Args>
auto makeObjectForMethod(T&&, Args&& ...args) -> get_class_t<decltype(&MyClass::funct)>
{
using R = get_class_t<decltype(&MyClass::funct)>;
return R{ std::forward(args)... };
}
int main()
{
auto myObj = makeObjectForMethod(&MyClass::funct);
myObj.funct();
return 0;
}
Works with C++11 and is quite handy: https://wandbox.org/permlink/usMa3fA0I2HCNJ7M
The only disadvantage that in case of class fields it is not very helpful.