通过宏扩展本题的解决方案:Pimpl idiom through Macro
我希望能够从 lambda 调用返回参考值:
#include <iostream>
#include <memory>
class FooImp
{
public:
int& C() { return _value; }
private:
int _value{};
};
class Foo
{
public:
Foo() :
_imp{ std::make_unique<FooImp>() }
{
}
int& C()
{
// In member function 'int& Foo::C()': cannot bind non-const lvalue reference
// of type 'int&' to an rvalue of type 'int'
return call_impl([&] { return _imp->C(); });
}
private:
template<typename fn_t>
auto call_impl(fn_t fn) -> decltype(fn())
{
std::cout << "Construct Measure here\n";
struct OnExit{
~OnExit() { std::cout << "Construct Log here\n"; }
} onExit;
return fn();
}
std::unique_ptr<FooImp> _imp;
};
int main()
{
Foo foo;
std::cout << foo.C() << "\n";
return 0;
}
Run Code Online (Sandbox Code Playgroud)
这给了我错误:
#include <iostream>
#include <memory>
class FooImp
{
public:
int& C() { return _value; }
private:
int _value{};
};
class Foo
{
public:
Foo() :
_imp{ std::make_unique<FooImp>() }
{
}
int& C()
{
// In member function 'int& Foo::C()': cannot bind non-const lvalue reference
// of type 'int&' to an rvalue of type 'int'
return call_impl([&] { return _imp->C(); });
}
private:
template<typename fn_t>
auto call_impl(fn_t fn) -> decltype(fn())
{
std::cout << "Construct Measure here\n";
struct OnExit{
~OnExit() { std::cout << "Construct Log here\n"; }
} onExit;
return fn();
}
std::unique_ptr<FooImp> _imp;
};
int main()
{
Foo foo;
std::cout << foo.C() << "\n";
return 0;
}
Run Code Online (Sandbox Code Playgroud)
因为我无法返回引用中临时创建的值。是否有任何可能的解决方案来使用call_impl
以引用作为返回值的方法?
返回类型应该是decltype(auto)
:
[&]() -> decltype(auto) {return _imp->C();}
Run Code Online (Sandbox Code Playgroud)
这将从底层函数复制返回类型。或者在这种情况下您可以手动编写-> int &
或-> auto &
。