Some background to the issue
if I have a struct like
typedef struct {
idx_type type;
union {
char *str;
int num;
} val
} cust_idx;
and I have loops like this
for (i = 0; i < some_get(x); i++) {
some_fun(z, NULL, i);
}
that I want to refactor to use the struct like some_fun(z, idx)
where idx
is one of my cust_idx
structs, would it be best to keep i
as the loop counter and update idx
or change the for header to use idx.val.num
instead of i
?
For the purposes of this, assume idx_type
is an enum for string and number types, and all other fields will have macros, but I'm only going to use the IDX_NUM
macro here as I'm not worried about anything to do with idx.type
.
To sum up my concerns:
- Will it be readable? I don't want to leave behind a mess that someone will read and just shake their head...
- Is it advised against?
- Which of these is the best solution?
Struct field as loop counter
#define IDX_NUM(x) (x.val.num)
...
cust_idx j;
j.type = TYPE_num;
for (IDX_NUM(j) = 0; IDX_NUM(j) < some_get(x); IDX_NUM(j)++) {
some_fun(z, j);
}
This does the same as the original, but the using struct field/macro extends and complicates the for loop header in my opinion but it's still fairly understandable.
Modify struct with original counter
cust_idx j;
j.type = TYPE_num;
for (i = 0; i < some_get(x); i++) {
IDX_NUM(j) = i;
some_fun(z, j);
}
This results in the least changes from old code logically, but will end in by far the largest amount of code due to the add assignment lines.
Pointer to struct field
cust_idx j;
int *i = &(j.val.num);
j.type = TYPE_num;
for ((*i) = 0; (*i) < some_get(x); (*i)++) {
some_fun(z, j);
}
I'm not sure how good this would be in the long run, or if it's advised against.