Техника оптимизации под линуха

поиск максимума среди двух целых чисел без использования ветвлений


Компилятор msvc поддерживает замену ветвлений математическими операциями, однако, использует несколько другую технику, отдавая предпочтение инструкции SETcc, устанавливающая переменную в единицу, если условие сс истинно. Как показывает практика, msvc оптимизирует только ветвления константного типа, т. е. "if (n >
 m) a = 66; else a = 99;" еще оптимизируется, а "if (n >
 m) a = x; else a = y;" уже нет.

Компилятор gcc, использующий инструкцию условного присвоения CMOVcc, оптимизирует все конструкции типа min, max, set flags, abs и т. д., что существенно увеличивает производительность, однако, требует как минимум Pentium Pro (инструкция SETcc работает и на Intel 80386). За это отвечают ключи -fif-conversion

и -fif-conversion2, которые на платформе Intel эквивалентны друг другу. (Вообще говоря, gcc поддерживает множество ключей, отвечающих за ликвидацию ветвлений, однако, на платформе Intel они лишены смысла, поскольку в лексиконе x86 процессоров просто нет соответствующих команд, это вам не PDP?11, элегантность которой остается непревзойденной до сих пор и которая имена специальную команду "пропустить следующую машинную инструкцию, если условие cc истинно/ложно", — вот где был простор для избавления от ветвлений!).

Компилятор icl – единственный из всех трех, кто не заменяет ветвления математическими операциями (что в свете активной агитации за команды SBB/CMOVcc, развернутой компаний Intel, выглядит довольно странно). Во всяком случае компилятор не делает этого явно и в качестве компенсации предлагает использовать инстриксы и функции мультимедийной библиотеки SIMD. В частности, цикл вида:

short a[4], b[4], c[4];

for (i=0; i<4; i++)

       c[i] = a[i] >
b[i] ? a[i] : b[i];



Содержание раздела