自动是基于范围的循环中的可选关键字吗?

时间:2015-09-21 23:24:07

标签: c++ for-loop auto c++17

我记得有人曾经告诉过我,

  

“基于范围的for循环中不需要auto。它会   如果我们要删除它,会在语言中含糊不清。“

这是真实的陈述吗? 以下代码是否有效的C ++语法?

for (elem : range){...}  

我原以为这已经是有效的语法了,但是当我用as编译时 clang++ --std=c++1z,我看到以下错误:

range-based for loop requires type for loop variable
 for (elem: range){

编译器仍然将其识别为基于范围的for循环,那么为什么它也不能导出类​​型呢?

3 个答案:

答案 0 :(得分:10)

在:

for (elem : range){...}  

语法目前无效,但有人建议使用此有效语法,gcc 5.2( see it live )支持该语法:

#include <vector>

int main()
{
    std::vector<int> v ;

    for( elem : v )
    {
    }
}

如果我们在C ++ 14模式下尝试这个,它会说:

  

警告:基于范围的for循环,只有类型说明符可用   使用-std = c ++ 1z或-std = gnu ++ 1z

所以这显然可行,并已在gcc中实现。看起来此功能已在gcc 6.0中删除。

据我所知,这是在gcc中实现的,期望proposal N3853: Range-Based For-Loops: The Next Generation会被接受,但被拒绝且更新版本N3994说:

  

这更新了N3853(见[1]),它提出了语法&#34; for(elem:   范围)&#34;,通过添加对属性的支持和回答额外的   的问题。请参阅原始提案,了解背后的理由   此功能,此处不再重复。

我们可以看到它已被EWG issue 81拒绝,我们也可以从Urbana meeting minutes看到这一点。尽管该提案存在许多问题,但我认为STL在提案的问答部分提出了令人信服的一系列论点,我对该提案遭到拒绝感到失望。

答案 1 :(得分:4)

语法需要range-for语句的类型,即使它是autofor (elem : range) {...}是语法错误,所以从技术上讲,是的,这是真的,语言可以声明这相当于for (auto elem : range) {...}

但至少存在两个主要问题:

首先,for (T elem : range)不需要T才能使用auto。如果编译器看到for (elem,它将无法知道elem是来自外部作用域的某个typedef,还是新声明的变量。它并不含糊,但编译器正确处理有点复杂。

第二个是你接下来应该得到默认值的问题。可以为auto进行合法的论证。可以为auto &进行合法的论证。可以为const auto &进行合法的论证。目前的方法只是让程序员选择。对auto替换为decltype(auto)的一些人来说,可能(我不完全确定)也可以进行合法的论证。

答案 2 :(得分:2)

这对ELL来说真的是个问题......

这句话是用虚拟语气写的,这意味着它是在谈论纯粹假设的情况,而不是实际的语言规则。虚拟语气用于反事实情况。