如何在C中的for(;;)循环中初始化几个变量?

时间:2010-07-27 23:23:38

标签: c loops initialization for-loop

我认为可以在for循环中初始化几个变量:

for (int i = 0, char* ptr = bam; i < 10; i++) { ... }

但我发现这是不可能的。 GCC给出以下错误:

  

错误:'char'之前的预期unqualified-id

您是否真的无法在for循环中初始化不同类型的变量?

7 个答案:

答案 0 :(得分:44)

您可以(但通常不应该)使用本地结构类型。

for ( struct { int i; char* ptr; } loopy = { 0, bam };
      loopy.i < 10 && * loopy.ptr != 0;
      ++ loopy.i, ++ loopy.ptr )
    { ... }

从C ++ 11开始,您可以更优雅地初始化各个部分,只要它们不依赖于局部变量:

for ( struct { int i = 0; std::string status; } loop;
      loop.status != "done"; ++ loop.i )
    { ... }

这几乎是可读的,无法真正使用。


C ++ 17计划解决结构化绑定的问题:

for ( auto [ i, status ] = { 0, ""s }; status != "done"; ++ i )

然而,详细的功能集和语法仍在不断变化。

答案 1 :(得分:17)

确实,您无法同时声明和初始化不同类型的声明符。但这并不是特定于for循环。如果你这样做,你会收到错误:

int i = 0, char *ptr = bam;

太。 for循环的第一个子句可以是(C99§6.8.5.3)“声明”或“void表达式”。请注意,您可以这样做:

int i = 0, *j = NULL;
for(int i = 0, *j = NULL;;){}

因为i*j都属于int类型。声明的确切语法在§6.7

中给出

答案 2 :(得分:12)

如果你真的需要变量留在循环范围内,你可以编写

{ char* ptr = bam; for (int i = 0; i < 10; i++) { ... } }

这有点难看,但有效。

答案 3 :(得分:7)

试试这个:

int i;
char* ptr;
for (i = 0, ptr = bam; i < 10; i++) { ... }

答案 4 :(得分:0)

您也可以这样做:

for (int i = 0; i < 10; i++) {
    static char* ptr = bam;
}

答案 5 :(得分:-2)

根据http://linuxsoftware.co.nz/cppgrammar.html#for-init-statement,您只能在for-init语句中获得简单声明或表达式(不允许包含声明)。这意味着答案是否定的(如果我正确地分析了BNF :))

答案 6 :(得分:-3)

我认为这些天他们教给你孩子的语言是为了给你带来手铐并腐烂你的大脑,这样你就可以保持安静,并将乐高积木放在一起,以非常有限的形式将它们拼凑在一起,这样你就可以建立平庸东西。 C的美妙之处在于,您可以遵循规则,并以巧妙的方式获得您想要的东西。以下是使用额外初始化程序编写此循环的方法。这是一个工作示例,向您展示如何将扩展循环桥接到第一个循环。您使用第一个来盗取其变量,它们仍在范围内。您使用虚拟变量使外循环运行一次。一个聪明的编译器会注意到这个事实并用循环展开器来核对循环。所以对你来说这只是好处。然后第二个数组使用第一个声明和第二个声明中的一些变量并运行完成。这是一个微不足道的例子,只是意味着你能够理解如何做到这一点,而不需要在一些范围内投入大量的动作。因为这样的技术可以像这样编写时使用宏来创建漂亮的下一代类似结构枚举,比如&#34;对于数组中的值,我有很多。

#include "stdio.h"
int
main(int argc, char **argv)
{
    const int max=7;
    const char *array[7] = {
    "hello","you","kids","who","don't","know","malloc\n"
    };

    for(int i=0,count=max,$=1;$;$=0)
    for(const char **p=array;count<max;i++)
    {
        printf("%s ",p[i]);
    }
}

这里没有任何遗漏。这个for循环连接的技术已经被用于嵌入调用以获取此散列对象的枚举器,并启动枚举,获取为键和值提取的值,并且还通过便利创建它们作为用户的void指针,他只需要命名它们。然后它们被填充,枚举将继续,直到完成所有键和值。如果用户在迭代中断,整个级联的onehot forloops将会像我们想要的那样分崩离析,因为它们可能甚至不存在,因为它们是由简单的const操作构造的,编译器可以看到它将展开循环。所以基本上它允许你扩展语法来做这样的事情,没有任何惩罚。

但是你需要知道一点C,并且至少让你的脑袋离开学校用这些玩具语言放置它们的机器人盒子。