Разница в том, что при #define
или enum
значение 3 не обязательно должно существовать как явное значение в коде, и поэтому компилятор решил использовать две инструкции добавления, а не выделять место для константы 3 Инструкция add reg,reg
составляет 2 байта на инструкцию, то есть 6 байтов инструкций и 0 байтов для умножения констант на 3, это меньший код, чем imul
плюс 4 байта константы. Кроме того, способ использования инструкций добавления позволяет получить довольно буквальный перевод * 2 * 3, так что это может быть не оптимизация размера, это может быть вывод компилятора по умолчанию всякий раз, когда вы умножаете на 2 или на 3. (добавить обычно более быстрая инструкция, чем умножение).
#define
и enum
не объявляют экземпляр, они только предоставляют способ дать символическое имя значению 3, поэтому у компилятора есть возможность сделать меньший код.
mov $0x1, -0x4(%ebp) ; r=1
mov -0x4(%ebp), %edx ; edx = r
mov %edx, %eax ; eax = edx
add %eax, %eax ; *2
add %edx, %eax ;
add %eax, %eax ; *3
mov %eax, -0x8(%ebp) ; a = eax
Но когда вы объявляете const int pi = 3
, вы указываете компилятору выделить пространство для целочисленного значения и инициализировать его значением 3. Это использует 4 байта, но константа теперь доступна для использования в качестве операнда для инструкции imul
,
movl $0x3, -0x8(%ebp) ; pi = 3
movl $0x3, -0x4(%ebp) ; r = 3? (typo?)
mov -0x4(%ebp), %eax ; eax = r
add %eax, %eax ; *2
imul -0x8(%ebp), %eax ; *pi
mov %eax, 0xc(%ebp) ; a = eax
Кстати, это явно не оптимизированный код. Поскольку значение a
никогда не используется, поэтому, если оптимизация была включена, компилятор просто выполнил бы
xor eax, eax ; return 0
Во всех 3 случаях.
Приложение:
Я пробовал это с MSVC, и в режиме отладки я получаю одинаковый вывод для всех 3 случаев, MSVC всегда использует imul с помощью литерала 6. Даже в случае 3, когда он создает const int = 3
, он фактически не ссылается на него Имуль.
Я не думаю, что этот тест действительно говорит вам что-то о const vs define vs enum, потому что это неоптимизированный код.