Параметры -O* задают удобные «пакеты» флагов оптимизации; параметры -f* (описанные позже) задают отдельные оптимизации, которые следует включить/выключить; параметры -m* задают специфичные для машины оптимизации, которые следует включить/выключить.
Большинство этих параметров являются булевыми и имеют параметры для включения и выключения (начинаются с префикса no-). Например, в то время как -fspecialise включает специализацию, -fno-specialise её отключает. Когда несколько флагов для одного и того же параметра появляются в командной строке, они оцениваются слева направо. Например, -fno-specialise -fspecialise включит специализацию.
Важно отметить, что флаги -O* примерно эквивалентны комбинациям флагов -f*. По этой причине эффект флагов -O* и -f* зависит от порядка их появления в командной строке.
Например, рассмотрим пример -fno-specialise -O1. Несмотря на то, что -fno-specialise появляется в командной строке, специализация по-прежнему будет включена. Это так, потому что -O1 подразумевает -fspecialise, переопределяя предыдущий флаг. В противоположность этому, -O1 -fno-specialise будет компилироваться без специализации, как и ожидалось.
5.3.1. -O*: удобные «пакеты» флагов оптимизации.
Существует множество параметров, влияющих на качество кода, генерируемого GHC. У большинства людей есть только общая цель, например, «Компилировать быстро» или «Заставить мою программу работать как по маслу». Следующие «пакеты» оптимизаций (или их отсутствие) должны быть достаточными.
Обратите внимание, что более высокие уровни оптимизации приводят к выполнению большего количества межмодульной оптимизации, что может повлиять на то, сколько вашей программы нужно перекомпилировать при внесении изменений. Это одна из причин придерживаться отсутствия оптимизации при разработке кода.
Если параметр типа ``-O*`` не указан: это означает «Пожалуйста, скомпилируйте быстро; я не слишком беспокоюсь о качестве скомпилированного кода». Например, ghc -c Foo.hs
-
-O0 -
Означает «выключить все оптимизации», возвращаясь к тем же настройкам, что и без указания параметров
-O. Указание-O0может быть полезно, если, например,makeуже вставил-Oв командную строку.
-
-O -
-O1 -
Означает: «Сгенерировать код хорошего качества, не тратя слишком много времени». Например:
ghc -c -O Main.lhs
-
-O2 -
Означает: «Применить все безопасные оптимизации, даже если это займет значительно больше времени на компиляцию».
Избегаемые «опасные» оптимизации — это те, которые могут ухудшить время выполнения или занимаемое пространство, если вам не повезёт. Обычно они включаются или выключаются индивидуально.
-
-O⟨n⟩ -
Любой -On, где n > 2, эквивалентен -O2.
Мы не используем флаг -O* для повседневной работы. Мы используем -O для получения приемлемой скорости; например, когда мы хотим что-то измерить. Когда мы хотим пойти ва-банк, мы, как правило, используем -O2 (и делаем много кофе-пауз).
Самый простой способ понять, что -O (и т. д.) «на самом деле означают», — это запустить -v и откинуться назад, поражёнными.