繁体   English   中英

为什么operator()在C ++ 17中为std :: function改变?

[英]Why does operator() change for std::function in C++17?

以下代码在C ++ 14中被认为是非法的,但在C ++ 17中是合法的:

#include <functional>

int main()
{
    int x = 1729;
    std::function<void (int&)> f(
        [](int& r) { return ++r; });
    f(x);
}

不要费心去测试它,你会得到不一致的结果,因此难以判断它是一个bug还是故意的行为。 但是,比较两个草稿(N4140和N4527,两者都可以在github.com/cplusplus/draft上找到),[func.wrap.func.inv]有一个显着的区别。 第2段:

返回:如果R为空则无效,否则返回值为INVOKE(f,std :: forward(args)...,R)。

在草稿之间删除了上述内容。 这意味着lambda的返回值现在被静默丢弃 这似乎是一种错误。 任何人都可以解释这个推理吗?

关于std::function<void(Args...)> 的标准中存在一个荒谬的缺陷 根据标准的措辞,没有(非平凡) 1使用std::function<void(Args...)>是合法的,因为没有任何东西可以“隐式转换为” void (甚至void )。

void foo() {} std::function<void()> f = foo; 在C ++ 14中不合法。 哎呀。

有些编译器采用了错误的措辞,使得std::function<void(Args...)>完全无用,并且仅将逻辑应用于传入的callables,其中返回值不为 void 然后他们得出结论,将一个返回int的函数传递给std::function<void(Args...)> (或任何其他非void类型)是违法的。 他们没有把它带到逻辑端并禁止函数返回voidstd::function要求对于完全匹配的签名没有特殊情况:相同的逻辑适用。)

其他编译器只是忽略了void返回类型情况下的错误措辞。

缺陷基本上是调用表达式的返回类型必须可以隐式转换为std::function的签名的返回类型(有关更多详细信息,请参阅上面的链接)。 根据标准, void不能隐式转换为void 2

所以缺陷得到了解决。 std::function<void(Args...)>现在接受任何可以使用Args...调用的东西,并丢弃返回值,就像许多现有的编译器一样。 我认为这是因为(A)语言设计者从未想过限制,或者(B)想要一种丢弃返回值的std::function的方法。

std::function 从未要求完全匹配参数或返回值,只是兼容性。 如果传入的参数可以从签名参数隐式转换,并且返回类型可以隐式转换为返回类型,那么它很高兴。

并且int(int&)类型的函数在许多直观定义下与签名void(int&)兼容,因为您可以在“void context”中运行它。


1基本上,不允许任何使operator()合法调用的东西。 你可以创建它,你可以销毁它,你可以测试它(并知道它是空的)。 你不能给它一个函数,即使是一个与其签名完全匹配的函数,或函数对象或lambda。 荒谬。

2对于void被impliclty转换成void的标准下,它要求的语句void x = blah; ,其中blah是void类型的表达式,是有效的; 该语句无效,因为您无法创建void类型的变量。

std::tie 用于 C++17 结构运算符<!--?</div--><div id="text_translate"><p> 考虑以下 C++17 结构:</p><pre> struct S { M1 m1; M2 m2; M3 m3; bool operator<(const S& that) const { return tie() < that.tie(); } auto tie() const { return std::tie(m1,m2,m3); } };</pre><p> 这个对吗? S::tie会返回成员引用的元组,还是会复制一份? 会自动推断出正确的类型(引用元组)吗? constness 做正确的事吗?</p><p> (我看到的示例对 std::tie 进行了两次调用,并且没有像这样分解为单独的成员 function。想知道/怀疑是否有原因。)</p></div>

[英]std::tie for C++17 struct operator<?

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM