Я сократил свой код до следующего, который настолько прост, насколько я мог бы его сделать, сохранив интересующий меня вывод компилятора.
void foo(const uint64_t used)
{
uint64_t ar[100];
for(int i = 0; i < 100; ++i)
{
ar[i] = some_global_array[i];
}
const uint64_t mask = ar[0];
if((used & mask) != 0)
{
return;
}
bar(ar); // Not inlined
}
Использование VC10 с / O2 и / Ob1,сгенерированная сборка в значительной степени отражает порядок инструкций в приведенном выше коде C ++.Поскольку локальный массив ar
передается в bar()
только в случае сбоя условия и в противном случае не используется, я ожидал бы, что компилятор оптимизируется до чего-то подобного следующему.
if((used & some_global_array[0]) != 0)
{
return;
}
// Now do the copying to ar and call bar(ar)...
Является ли компиляторне делать этого, потому что для него слишком сложно определить такие оптимизации в общем случае?Или он следует строгому правилу, запрещающему это делать?Если так, то почему, и есть ли какой-то способ, которым я могу дать подсказку, что это не изменит семантику моей программы?
Примечание: очевидно, было бы тривиально получить оптимизированный вывод, просто переставивкод, но меня интересует , почему компилятор не будет оптимизировать в таких случаях, а не как сделать это в этом (намеренно упрощенном) случае.