C++ lazy constructor I'm implementing a lazy constructor in C++. The goal is that for a type T, lazy&lt;T&gt;(args...) returns a callable object which, when called, returns T(args...).

This is what I have done so far:

#include &lt;functional&gt;
#include &lt;utility&gt;

/**
 * Returns an object of type `T` constructed from `args`.
 */
template&lt;typename T, typename... Args&gt;
T make(Args&amp;&amp;... args)
{
    return T(std::forward&lt;Args&gt;(args)...);
}

/**
 * Wrap a value of type `T` and perfect-forward it when accessed.
 */
template&lt;typename T&gt;
class Forward {
public:
    Forward(T &amp;&amp;value) noexcept : value_(std::forward&lt;T&gt;(value))
    {}

    operator T()
    {
        return std::forward&lt;T&gt;(value_);
    }

private:
    T value_;
};

/**
 * Returns a callable object which, when called, returns
 * an object of type `T` constructed from `args`.
 */
template&lt;typename T, typename... Args&gt;
auto lazy(Args&amp;&amp;... args) -&gt; decltype(
        std::bind(
            make&lt;T, Args...&gt;,
            Forward&lt;Args&gt;(std::forward&lt;Args&gt;(args))...))
{
    return std::bind(
            make&lt;T, Args...&gt;,
            Forward&lt;Args&gt;(std::forward&lt;Args&gt;(args))...);
}


(Contrived) Examples:

// rvalue arguments
auto makePtr = lazy&lt;std::unique_ptr&lt;int&gt;&gt;(new int(123));
auto ptr = makePtr();

// lvalue arguments
int *rawPtr = new int(456);
auto makePtr2 = lazy&lt;std::unique_ptr&lt;int&gt;&gt;(rawPtr);
auto ptr2 = makePtr2();


Can this code be improved (particularly in terms of efficiency)?

UPDATE: The Forward class is used only as arguments to std::bind. Rationale:

Suppose we have a type Foo with constructor Foo(const std::unique_ptr&lt;int&gt; &amp;). We can construct it by calling make&lt;Foo, const std::unique_ptr&lt;int&gt; &amp;&gt;(someUniquePtr), for example.

However, std::bind(make&lt;Foo, const std::unique_ptr&lt;int&gt; &amp;&gt;, someUniquePtr)() won't work (I think), because the reference-ness of the second argument to std::bind will be dropped. Wrapping it inside a std::cref works, but for packed arguments it seems the Forward class is the only solution I can come up with that works for all types.

It's possible that I misinterpreted the cause of this but here is an example of what I mean: https://godbolt.org/g/8w2Msa.
I think you can really simplify your code with the use of lambdas.

template&lt;typename T, typename... Args&gt;
auto make_lazy(Args&amp;&amp;... args)
{
    return [=]{return T(std::move(args)...);};
}


Usage example:

#include &lt;iostream&gt;
class T
{
    int v;
    public:
        T(int v): v(v) {std::cout &lt;&lt; "Building T\n";}
        friend std::ostream&amp; operator&lt;&lt;(std::ostream&amp; s, T const&amp; out) {return s &lt;&lt; "T: " &lt;&lt; out.v &lt;&lt; "\n";}
};
class S
{
    int v;
    public:
        S(int v): v(v) {std::cout &lt;&lt; "Building S\n";}
        friend std::ostream&amp; operator&lt;&lt;(std::ostream&amp; s, S const&amp; out) {return s &lt;&lt; "S: " &lt;&lt; out.v &lt;&lt; "\n";}
};

template&lt;typename T, typename... Args&gt;
auto make_lazy(Args&amp;&amp;... args)
{
    return [=]{return T(std::move(args)...);};
}

int main()
{
    auto lazyT = make_lazy&lt;T&gt;(1);
    auto lazyS = make_lazy&lt;S&gt;(2);

    std::cout &lt;&lt; "Building\n";
    std::cout &lt;&lt; lazyT() &lt;&lt; "\n";
    std::cout &lt;&lt; lazyS() &lt;&lt; "\n";
}