Который более эффективен в Haskell; сопоставление с образцом или вложенный, если/операторы выбора?

Символ = выделяет значение арифметического выражения справа от переменной слева

blockquote>

Он присваивает результат. Распределение - это нечто иное, и важно помнить разницу позже (в частности, динамическое распределение будет очень запутанным, если вы сопоставите его с назначением).

Но если у меня есть такое выражение, как x += y % 3, значит ли это x = (x + y) % 3 или x = x + (y % 3)?

blockquote>

Отчасти из-за наличия соединения +=, -= и т. Д. Операторы в том, что вы не не расширяете выражение, как это, избегая неоднозначности, создаваемой вашей перезаписью.

x += y % 3

можно читать как

tmp = y % 3; // evaluate right hand side
x += tmp;    // assign to left hand side

(вы можете расширить x += tmp до x = x + tmp, если действительно хотите, после tmp было оценено) . [+1122]

Все правила описаны здесь здесь в любом случае, и в любом случае вы можете просто протестировать некоторый код для проверки: https://ideone.com/81tvjH [ 1112] [+1123]

11
задан C. A. McCann 17 December 2011 в 22:58
поделиться

3 ответа

В Haskell, case и сопоставление с образцом неразрывно связано; Вы не можете иметь один без другого. if p then e1 else e2 синтаксический сахар для case p of { True -> e1; False -> e2 }. По этим причинам я думаю, что невозможно произвести примеры, которые Вы просите; в Core Haskell все эквивалентно case.

На языках в семействе ML оптимизатор может часто делать очень впечатляющие вещи со сложными соответствиями шаблона. Это более трудно для компиляторов Haskell; из-за отложенных вычислений компилятору соответствия шаблона не позволяют переупорядочить определенные тесты. Другими словами, если Вы вкладываете case операторы по-разному, можно получить другую производительность, но в Haskell Вы также получаете другую семантику. Таким образом, обычно компилятор не смешивает с ним.

До которого способа написать Ваш собственный код, безопасно предположить, что код с наименьшим количеством case-выражений является лучшим (учет того факта, что один if эквивалентно одному case-выражению).

20
ответ дан 3 December 2019 в 02:30
поделиться

Я не подтвердил это, но я думаю, что обе формы станут вложенным случаем - выражения при переводе для удаления сердцевины Haskell компилятором. Лучший способ узнать спрашивает сам компилятор. В GHC можно включить дамп базовой промежуточной программы при помощи аргументов:

  • Перед упрощениями:-ddump-ds
  • После упрощений:-ddump-simpl
7
ответ дан 3 December 2019 в 02:30
поделиться

Согласно спецификации, они семантически эквивалентны. Это, конечно, не обязательно означает, что они реализованы тождественно, но я был бы лично удивлен, было ли различие в достойном компиляторе.

5
ответ дан 3 December 2019 в 02:30
поделиться
Другие вопросы по тегам:

Похожие вопросы: