简体   繁体   中英

How to determine the return type of a function in template

I am trying to write a class similar to std::function, just to learn how it works but I am having problem determining the return type of the function.

I found this from one of the answers here on stack overflow. I am trying to do something similar but It does not work and I do not know why.

template< class Fx >
class function
{
public:
    function() = default;

    function(Fx* fx)
    {
        this->fx = fx;
    }
        
    template < class... A >
    ReturnType operator()(A... args)
    {
        //return ((*fx)(args), ...); ??
    }

private:
    template<class F>
    struct return_type;

    template< class R, class... A>
    struct return_type<R(*)(A...)>
    {
        using type = R;
    };

    using ReturnType = return_type<Fx>::type;
    Fx* fx;
};


int sum(int a, int b) { return a + b; };

int main()
{
    function<int(int, int)> mysum{ sum };
    mysum(10, 10);
}

It gives me an error on line

using ReturnType = return_type<Fx>::type;

saying incomplete type is not allowed. Why does it not pick the specialized one?

Since Fx is supposed to be a function type, not a function pointer type, so the specialization should be declared as:

template< class R, class... A>
struct return_type<R(A...)>
{
    using type = R;
};

Other issues:

  1. Change using ReturnType = return_type<Fx>::type; to using ReturnType = typename return_type<Fx>::type; .

  2. Move the declaration of ReturnType (and definition of return_type ) before using it as the return type of operator() .

  3. Change return ((*fx)(args), ...); to return (*fx)(args...); in the operator() ; ie all the arguments are supposed to be passed to fx instead of calling fx multiple times with each argument.

LIVE

BTW: Return type deduction (since C++14) is worthy of consideration too. Eg

template < class... A >
auto operator()(A... args)
{
    return (*fx)(args...);
}

LIVE

You should change your template in the class instantiation:

template <typename R, typename ...Args>
class function {
    ...
    R operator()(Args... args){
        return fx(...args)
    }
}

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