Does C have a “foreach” loop construct?

前端 未结 12 2218
情书的邮戳
情书的邮戳 2020-12-02 03:49

Almost all languages have a foreach loop or something similar. Does C have one? Can you post some example code?

12条回答
  •  一向
    一向 (楼主)
    2020-12-02 04:29

    As you probably already know, there's no "foreach"-style loop in C.

    Although there are already tons of great macros provided here to work around this, maybe you'll find this macro useful:

    // "length" is the length of the array.   
    #define each(item, array, length) \
    (typeof(*(array)) *p = (array), (item) = *p; p < &((array)[length]); p++, (item) = *p)
    

    ...which can be used with for (as in for each (...)).

    Advantages of this approach:

    • item is declared and incremented within the for statement (just like in Python!).
    • Seems to work on any 1-dimensional array
    • All variables created in macro (p, item), aren't visible outside the scope of the loop (since they're declared in the for loop header).

    Disadvantages:

    • Doesn't work for multi-dimensional arrays
    • Relies on typeof(), which is a GNU extension, not part of standard C
    • Since it declares variables in the for loop header, it only works in C11 or later.

    Just to save you some time, here's how you could test it:

    typedef struct {
        double x;
        double y;
    } Point;
    
    int main(void) {
        double some_nums[] = {4.2, 4.32, -9.9, 7.0};
        for each (element, some_nums, 4)
            printf("element = %lf\n", element);
    
        int numbers[] = {4, 2, 99, -3, 54};
        // Just demonstrating it can be used like a normal for loop
        for each (number, numbers, 5) { 
            printf("number = %d\n", number);
            if (number % 2 == 0)
                    printf("%d is even.\n", number);
        }
    
        char* dictionary[] = {"Hello", "World"};
        for each (word, dictionary, 2)
            printf("word = '%s'\n", word);
    
        Point points[] = {{3.4, 4.2}, {9.9, 6.7}, {-9.8, 7.0}};
        for each (point, points, 3)
            printf("point = (%lf, %lf)\n", point.x, point.y);
    
        // Neither p, element, number or word are visible outside the scope of
        // their respective for loops. Try to see if these printfs work
        // (they shouldn't):
        // printf("*p = %s", *p);
        // printf("word = %s", word);
    
        return 0;
    }
    

    Seems to work on gcc and clang by default; haven't tested other compilers.

提交回复
热议问题