I have hotspot code which runs in a tight loop:
for (i = 0; i < big; i++)
{
if (condition1) {
do1();
} else if (condition2) {
do2();
} else {
do3();
}
// Shared code goes here
// More shared code goes here
}
Since condition1
and condition2
are invariant, I unswitched the loop to
if (condition1) {
for (i = 0; i < big; i++)
{
do1();
// Shared code goes here
// More shared code goes here
}
} else if (condition 2) {
for (i = 0; i < big; i++)
{
do2();
// Shared code goes here
// More shared code goes here
}
} else {
for (i = 0; i < big; i++)
{
do3();
// Shared code goes here
// More shared code goes here
}
}
This runs much better, but I wonder if there's a clever way to do this without repeating myself?
Another, possibly slightly more efficient option is to use a macro to construct the code for you:
#define DO_N(name, ...) for(int i = 0; i < big; i++){name(__VA_ARGS__);/*shared code*/}
if (condition1) {
DO_N(do1, .../*arguments here*/)
} else if (condition 2) {
DO_N(do2, ...)
} else {
DO_N(do3, ...)
}
#undef DO_N
Its ugly, but I think it does what you want, and might allow inlining where a function pointer does not.
Additionally, you may find it more readable to put your shared code in a separate macro or function.
I think you can declare a function pointer and some function foo()
:
typedef void (*fp)(void);
void foo(int big, fp f) {
for (int i = 0; i < big; ++i) {
f();
// Shared code goes here
// More shared code goes her
}
}
Then change your code for something like this:
if (condition1) {
foo(big, do1);
} else if (condition2) {
foo(big, do2);
} else {
foo(big, do3);
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With