参见英文答案 >
Using `std::function<void(…)>` to call non-void function3个
根据C 11或C 14标准,下面的代码是否有效?
根据C 11或C 14标准,下面的代码是否有效?
#include <functional> int ReturnInt() { return 5; } int main( int argc,char **argv ) { std::function< void () > BoundType = ReturnInt; return 0; }
该代码可以使用最新的gg(4.8.3)和clang(4.3.2)的cygwin版本编译,但不适用于Visual Studio 2013,Visual Studio 2013年11月的CTP或Visual Studio 14预览版.如果将std :: function更改为boost :: function,它也会在所有平台上编译.
我发现this其他堆栈溢出问题表明它应该工作.
解决方法
代码在C 11中是未定义的行为,在C 14中是不正确的.C 14将此备注添加到此构造函数的规范中:
Remarks: These constructors shall not participate in overload
resolution unlessf
is Callable (20.9.11.2) for argument types
ArgTypes...
and return typeR
.
Callable在[func.wrap.func] / p2中定义:
A callable object
f
of typeF
is Callable for argument typesArgTypes
and return typeR
if the expression INVOKE(f,declval<ArgTypes>()...,R)
,considered as an unevaluated operand
(Clause 5),is well formed (20.9.2).
为了使INVOKE形成良好,不带R的INVOKE的返回类型必须可以隐式转换为R([func.require] / p2).
在C 11中,这些语句属于Requries子句,这意味着由客户端决定是否正确,如果客户端失败,任何事情都可能发生,包括成功编译.
这被LWG 2132改变了.