
Best Practices for Array Indexing - bollu
http://bollu.github.io/#best-practices-for-array-indexing
======
shakna
There's two basic ways of defining iterators in C to remove some pain points.
(There's others, but these two common patterns crop up often enough.)

    
    
        void foreach(TYPE* o, void(*f)(TYPE, void*), void* f_state)
    

Which you would use like:

    
    
        static void sum_bytes(wchar_t c, void* state) {
          *((size_t*) state) += c;
        }
    
        size_t sum = 0;
        foreach(jstr, sum_bytes, (void*)&sum);
    

An iterator that runs some function repeatedly against each element of the
object, with the ability to pass in some kind of state. Tiny bit more advanced
than the more common:

    
    
        size_t first(TYPE* o) { return 0; }
        size_t end(TYPE* o, size_t position) { return position >= len(o); }
        size_t next(TYPE* o, size_t position) { return position + 1; }
    

Which you would use like:

    
    
        for(size_t i = first(o); !end(o, i); i = next(o, i)) {
        }
    

Hiding your indexing ideas inside abstractions that you can write once, and
use continually, removes some cognitive load, and means that when you find
your pesky off-by-one error, it's only in one place, not a half-dozen nearly-
matching-but-not-quite patterns.

------
BubRoss
tl;dr - a lot of mental energy going to avoiding making mistakes with indexed
loops when iterators or macro that iterates but gives you an index inside the
loop could be used.

