I'd like to be able to use template deduction to achieve the following:
GCPtr<A> ptr1 = GC::Allocate();
GCPtr<B> ptr2 = GC::Allocate();
instead of (what I currently have):
GCPtr<A> ptr1 = GC::Allocate<A>();
GCPtr<B> ptr2 = GC::Allocate<B>();
My current Allocate function looks like this:
class GC
{
public:
template <typename T>
static GCPtr<T> Allocate();
};
Would this be possible to knock off the extra <A>
and <B>
?
That cannot be done. The return type does not take part in type deduction, it is rather a result of having already matched the appropriate template signature. You can, nevertheless, hide it from most uses as:
Whether that syntax is actually any better or worse than the initial
GCPtr<A> p = GC::Allocate<A>()
is another question.P.S. c++11 will allow you to skip one of the type declarations:
(This answer is the same as @UncleBens, but a bit more general as it perfect-forward any arguments.)
This is very useful in languages like haskell where, for example,
read
will take a string as input and will parse it according to the desired return type.(Here is sample code on ideone.)
First, start with the function
foo
whose return type we wish to deduce:When asked for a string, it'll return the string that's in its first argument. When asked for an int, it'll return the second argument.
We can define a function
auto_foo
that can be used as follows:To make this work, we need an object that will temporarily store the function arguments, and also run the function when it is asked to convert to the desired return type:
Also, the above works for two-arg or three-arg functions, it's not difficult to see how to extend that.
This is a lot of code to write! For each function you will to apply this to, you could write a macro that does this for you. Something like this at the top of your file:
and then you could use
auto_foo
in your program.In the same way you can't overload functions on return type, you can't do template deduction on it. And for the same reason - if f() is a template/overload that returns something, what type to use here:
You could try to use a macro for it. Other than that, I don't see how that's supposed to work with just one statement.
Johannes' points are valid. The >> issue is easily fixed. But I think having commas as part of the type requires the C99 preprocessor varargs extension:
The only thing I can think of: make Allocate a non-template that returns a non-template proxy object that has a templated conversion operator which does the real work:
You could go the opposite route.
If you're using an up to date compiler (MSVC 2010 which should be out in a couple of days, or the current version of GCC) and don't mind relying on C++0x features:
would save you the extra
<A>
and<B>
, just not on the right hand side. :)