Doing generic foreach loops in C

While doing some work with linked lists, I looked into making an iterator loop. I wanted it to be generic without too much #define magic so as to still be readable for the average C programmer. I came up with this:

// gcc -Wall -g -o foreach foreach.c

#include <stdio.h>

#define foreach(item, list, ...)   { int t; typeof(list[0]) item; \
  for(t=0, item=list[0]; t<sizeof(list) / sizeof(list[0]); t++, item=list[t]) \
  { __VA_ARGS__ ; } }

int main(int argc, char *argv[])
{
int i[] = { 2, 5, 7, 8, 10, 12 };        // 6 elements
char *s[] = { "one", "two", "three" };   // 3 elements

foreach(g, i, g++; printf("%u\n", g););

foreach(g, s, printf("%s\n", g););

return 0;
}

This code defines two arrays and uses the same mechanism to print the values of both. As you can see in the integer loop, you can write multiple statements and even modify the item.

This #define keeps variables that are declared in its own scope, so they don’t leak out. The item type is set automatically via the typeof() GCC extension. By using sizeof() I determine the length of the array.

The only cosmetic issue is that, what you normally put in a block behind the for() loop, is now put as the third argument in the foreach() statement. It shouldn’t be of any practical hindrance though.

If you’ve got suggestions for improvements, let me know.

Leave a Comment

Your email address will not be published. Required fields are marked *