LINUX.ORG.RU

Монады vs макросы vs фекспры

 , , ,


3

4

Эти все вещи имеют нечто общее — контроль над порядком вычислений. Однако, почему то, я никогда не видел сравнения их с этой точки зрения. Постараюсь восполнить этот пробел, а вы дополните, или возразите. Я привожу градацию в пороядке «от сильного к слабому»

1) fexprs. Имеют полный контроль над вычислениями.

2) macros. Имеют контроль над вычислениями, ограниченный временем компиляции.

3) monads. То же самое, что п. 2, за исключением того, что в теле функции невозможно получить само выражение аргумент, «как он есть», а лишь его вычисленное значение.

Возможно я ошибаюсь, поэтому дополняйте и исправляйте.

Ты сначала с lexical scope разберись, а потом уже в монады-говнады лезь.

anonymous
()

Эти все вещи имеют нечто общее — контроль над порядком вычислений

Монады в общем не контролируют порядок вычислений.

hateyoufeel ★★★★★
()

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

buddhist ★★★★★
()
Последнее исправление: buddhist (всего исправлений: 1)
Ответ на: комментарий от hateyoufeel

Контролируют, просто ты об этом пока не знаешь, с факториалом еще не разобрался. Если бы не контролировали, у тебя бы не было контроля над побочными эффектами.

terminator-101
() автор топика
Ответ на: комментарий от anonymous

какой такой порядок вычислений

Нормальный порядок вычислений позволяет контролировать сами вычисления, что вычислять а что нет, в этом смысле.

terminator-101
() автор топика
Ответ на: комментарий от terminator-101

Ты шизофреник. Переведи свою бредовую фразу на русский. Никакого такого порядка монада maybe не обеспечивает, она тупо служит более безопасным вариантом null.

anonymous
()
Ответ на: комментарий от terminator-101

Лол. //простите, не удержался.

ymn ★★★★★
()
Ответ на: комментарий от anonymous

А это уже рефлексия. То есть, понятно, что под капотом оно действительно так, но в явном виде все эти штуки нужны только в хаскеле и подобных ему языках.

buddhist ★★★★★
()
Ответ на: комментарий от buddhist

Они там в явном виде тоже не нужны, просто удобно иметь синтаксический сахар для монад. Ну так и в динамических языках его тоже полезно иметь, особенно для такой фундаментальной штуки, как maybe.

anonymous
()
Ответ на: комментарий от terminator-101

Ошибаешься. Монады порядок вычислений действительно не контролируют. То, что монады IO и STM это делают - скорее, их особенность.

Miguel ★★★★★
()
Ответ на: комментарий от buddhist

А что значит явный? Семантически, maybe может быть реализовано в языке с try/catch, явно.

terminator-101
() автор топика
Ответ на: комментарий от terminator-101

Контролируют, просто ты об этом пока не знаешь

Особенно Monad Reader. Контролирует, да.

hateyoufeel ★★★★★
()
Ответ на: комментарий от buddhist

В жизни не читал Душкина, хватило просмотра его ЖЖ.

Ну его не обязательно читать, чтобы быть упоротым на таком же уровне. Монады используются не только для выражения «побочных эффектов в статических языках», равно как и побочные эффекты в статических языках не обязательно выражаются с помощью монад.

fmdw
()
Ответ на: комментарий от fmdw

Монады используются не только для выражения «побочных эффектов в статических языках»
Мона́да в функциональном программировании — это абстракция линейной цепочки связанных вычислений. Её основное назначение — инкапсуляция функций с побочным эффектом от чистых функций, а точнее их выполнений от вычислений[1]. Монады применяются в языке Haskell, так как он повсеместно использует ленивые вычисления, которые вместе с побочным эффектом, как правило, образуют плохо прогнозируемый результат.

Может не исползуется, но сводится

terminator-101
() автор топика
Ответ на: комментарий от terminator-101

То, что ты привёл - полная хрень. Во-первых, есть монады, никак не контролирующие порядок вычислений. Про Reader я выше уже написал. Во-вторых, если варианты хаскелла, в которых IO работает без монад.

hateyoufeel ★★★★★
()
Ответ на: комментарий от terminator-101

Какую «цепочку вычислений» представляет собой монада []? Что в ней является побочным эффектом?

fmdw
()
Ответ на: комментарий от terminator-101

Ну и зачем ты, шизофреник, цитируешь бред какого-то другого шизофреника?

Еще раз, расскажи, какой такой порядок вычислений в монаде maybe?!?

anonymous
()
Ответ на: комментарий от hateyoufeel

То, что ты привёл - полная хрень

А почему бы тебе не переписать википедию?

terminator-101
() автор топика
Ответ на: комментарий от hateyoufeel

монады гарантируют порядок вычисления до WHNF.

Monads introduce sequencing (single-threading) into the functional world. In that sense, monadic computation emulates imperative computation. However, in the imperative world, statements execute in the order they are written because such is the semantics of an imperative language. We trust the system honoring our statement order, because the order of executing mutations is crucial to knowing the global state of the system at any point in time. In contrast, in monadic world there is no really global state. A state is explicitly passed from one computation to another. Two computations are executed in order because the second needs the result of the first.

топик не читал

qnikst ★★★★★
()
Ответ на: комментарий от qnikst

single-threading

Я, кстати, считаю, что это неверное выражение. В «функциональном мире» нет никакого «multi-threading». Есть банальная лень, ограниченная значениями. Один шаг редукции — одно вычисление.

terminator-101
() автор топика
Ответ на: комментарий от qnikst

Ссылку? В случае с простыми монадами типа вышеупомянутой Reader порядок вычислений не играет роли вообще. разве нет?

hateyoufeel ★★★★★
()
Ответ на: комментарий от qnikst

Не, а что, есть возражения? Это вообще-то, общеизвестный (не в кругах лоровских аналитегов), тривиальный факт. LC не обеспечивает параллелеизма.

terminator-101
() автор топика
Ответ на: комментарий от qnikst

монады гарантируют порядок вычисления до WHNF.

Да ладно? Смотрим исходники instance Monad для Maybe/[]/..., нигде не видим seq, убеждаемся, что bind не более гарантирует порядок вычисления до WHNF, чем (.).

fmdw
()
Ответ на: комментарий от hateyoufeel

Ссылку, не дам. Монада это такой тайпкласс, который приносит одну операцию - bind:

class Monad m where
  (>>=) :: m a -> (a -> m b) -> m b

Как ты видишь из типа, для того, чтобы выполнить действие a -> m b нам необходим результат из a, поэтому чтобы ты не делал выполнял сразу или строил какой план или ещё что, первое действие выполнится до творого. Так везде в IO, ST, Reader, Maybe, ну разве кроме MyBrokenMonad:

instance Monad MyBrokenMonad where _ >>= f = f undefined

В этом отличие от Applicative, в котором нету связи, соответвенно порядка нет, и можно вычислять как угодно с точностью до сохранения семантики.

Не стоит забывать, что мы говорим о вычислительном контексте, который задают структуры данных такие как Maybe, Reader или (->), IO:

  • Reader - вычисление окружением
  • Maybe - вычисление с возможным значением
  • List - вычисление с множественным количеством значений
  • IO - вычисление с произвольными эффектами

В любом из этих контекстов монадическая структура задает порядок.

qnikst ★★★★★
()
Последнее исправление: qnikst (всего исправлений: 1)
Ответ на: комментарий от qnikst

То есть, я хочу сказать, что не следовало бы употреблять фразы «покупай только у нас, в июне со скидкой...», «multisupertreading!!!», а достаточно просто: нормальный/аппликативный

terminator-101
() автор топика
Ответ на: комментарий от qnikst

Ты не со мной, а с Барендрегтом поспорь.

Хотя, надо признать, что ты наиболее адекватный фанбой из отписавшихся. Своими постами ты лишь подтвердил «чушь», которая в стартовом посте.

terminator-101
() автор топика
Ответ на: комментарий от terminator-101

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

qnikst ★★★★★
()
Ответ на: комментарий от qnikst

и почему я тебе не верю?

Понятия не имею, я не психиатр.

import Debug.Trace
import Control.Monad.State.Lazy

data Foo a b = Foo { a :: a, b :: b }

main = do
  let (r, s) = (flip runState) (Foo 1 1) $ do
        modify (\x -> x { a = trace "Should be 1st, right?" $ 2})
        modify (\x -> x { b = trace "Should be 2nd, right?" $ 2})
  print $ b s
  print $ a s

Should be 2nd, right? 2 Should be 1st, right? 2

fmdw
()

Все правильно сказал, тут нечего добавить. Так оно и есть. Поэтому, хаскель строго слабей чем лисп (и даже си с препоцессором). Кроме того, хаскель не обладает свойством самоописания. Невозможно реализовать хаскель на самом хаскеле — метациклический исполнитель. Он требует подпорок из-вне. Язык не консистентен.

anonymous
()
Ответ на: комментарий от qnikst

Как ты видишь из типа, для того, чтобы выполнить действие a -> m b нам необходим результат из a, поэтому чтобы ты не делал выполнял сразу или строил какой план или ещё что, первое действие выполнится до творого.

И где тут порядок действий?

В любом из этих контекстов монадическая структура задает порядок.

Не задает.

Waterlaz ★★★★★
()
Ответ на: комментарий от Waterlaz

И где тут порядок действий?

m >>= f — m вычислится до WHNF до f.

Если пытаетесь оспорить, то не забывайте приводить логическую цепочку или контр-пример.

qnikst ★★★★★
()
Ответ на: комментарий от Waterlaz

то, что происходит вычисление до WHNF. Если ты этого не понял, то может не стоит спорить?

qnikst ★★★★★
()
Ответ на: комментарий от qnikst

да, товарищи.. перед тем как спорить дальше, подумайте, чем Monad отличается от Applicative.

qnikst ★★★★★
()
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.