我可以创建返回std::optional<Foo>
的std::function
,并为其分配返回Foo
的lambda。有人能详细解释一下这是如何实现的吗?
简单的例子:
#include <iostream>
#include <optional>
#include <functional>
int main()
{
int k = 13;
std::function<std::optional<int>()> f1;
f1 = [&] {return k++;}; //implicite int
std::cout<<"k = " << f1().value() << std::endl;
f1 = [&] () -> int {return k;}; //explicite int
std::cout<<"k = " << f1().value() << std::endl;
}
std::optional
(重载集中的#8(的构造函数是有条件显式的,具体取决于模板参数。在您的案例(std::optional<int>
(中,您可以隐式地构造实例,
std::optional<int> opt;
opt = 42; /* No problem, implicit construction. */
而这正是包装器CCD_ 6所做的。它调用返回int
的包装函数,并使用此返回值隐式构造自己的返回值std::optional<int>
。
存在从int
到std::optional<int>
的隐式转换。
std::function
的模板构造函数使用命名的requirementCallable,它只要求INVOKE
表达式可以隐式转换为结果类型,而不要求它们是同一类型。
简而言之,分配给std::function
的目标必须是std::function
模板参数的参数和返回类型的Callable。
例如:给定:
- a
std::function<R(P1, P2)>
P1
型p1
P2
型p2
如果f(p1, p2)
格式良好并且可以隐式转换为R
,则可以将目标f
分配给它。(*(
其他答案表明CCD_ 23是由CCD_ 24隐式构造的。
因此,在您的示例中,[&] () -> int {return k;}()
返回一个int
,它可以隐式转换为std::optional<int>
。
(*(请注意,这有点过于简单,因为严格的定义涉及调用函数/概念