Control flow as a type
May. 24th, 2024 10:24 amЧем больше я про это думаю, тем больше я его хочу.
Любое замыкание (в расте) может управлять control flow приложения, но только в смысле panic!. Замыкание не может управлять другим control flow, например, break/continue/return.
Это делает не экивалентным цикл итератора и применение map для того же самого итератора. Несправедливо! Если бы только компилятор понимал управление control flow и мог правильно проверить его совместимость...
Любое замыкание (в расте) может управлять control flow приложения, но только в смысле panic!. Замыкание не может управлять другим control flow, например, break/continue/return.
Это делает не экивалентным цикл итератора и применение map для того же самого итератора. Несправедливо! Если бы только компилятор понимал управление control flow и мог правильно проверить его совместимость...
no subject
Date: 2024-05-24 08:28 am (UTC)no subject
Date: 2024-05-24 08:46 am (UTC)also, хочу узрить return return на монадках.
no subject
Date: 2024-05-24 09:01 am (UTC)Опишите, что он делает.
no subject
Date: 2024-05-24 09:06 am (UTC)Теперь попробуй это записать через filter/map:
no subject
Date: 2024-05-24 09:53 am (UTC)module Test where
import Control.Monad
testFn rc bc dv l = either id id $ (forM_ l $ \e -> if rc e then Left e else (if bc e then Left dv else return () ) ) >> return dv
*Test> testFn (==1) (==2) 0 [3,3,2,1]
0
*Test> testFn (==1) (==2) 0 [3,3,1,2]
1
no subject
Date: 2024-05-24 09:54 am (UTC)no subject
Date: 2024-05-24 10:58 am (UTC)Напиши без материализованного энума (без байтов в памяти) и в виде отдельной функции, которую ты вызываешь по имени.
Я плохо читаю хаскель и не могу понять, if выполняется внутри лябмды или снаружи.
no subject
Date: 2024-05-24 01:31 pm (UTC)Отчасти. инстанс монадки Either (эквивалент Result в Rust) написан так, что после первого Left ничего не вычисляется, там даже список не будет конструироваться. Кроме того, GHC умный, вполше может промежуточное построение Either optimize away.
>Я плохо читаю хаскель и не могу понять, if выполняется внутри лябмды или снаружи.
Внутри. Все if внутри лямбны, снаружи только монадка.
> Напиши без материализованного энума (без байтов в памяти) и в виде отдельной функции, которую ты вызываешь по имени.
Какие мы привередливые.
import Control.Monad.Cont testCn :: (a -> Bool) -> (a -> Bool) -> a -> [a] -> a -- ^ immidiate return condition checker, abort and return default value checker, default value, list to proc. testCn rc bc dv l = flip runCont id $ callCC $ \rexit -> do callCC $ \lexit -> forM_ l $ \e -> do when (rc e) $ rexit e when (bc e) $ lexit () return dvИспользуется монада продолжений, на которой можно сочинить любой разумный control flow. Первый callCC дает продолжение rexit (return-exit), которое позволяет выскочить из функции сразу, второй callCC дает продолжение, которое выскакивает перед
no subject
Date: 2024-05-27 09:22 am (UTC)no subject
Date: 2024-05-27 10:04 am (UTC)testCn rc bc dv l = flip runCont id $ callCC $ \rexit -> do { callCC $ \lexit -> forM_ l $ \e -> do{ when (rc e) $ rexit e; when (bc e) $ lexit (); }; return dv; }runCont - раскрывает монадку продолжения
callCC - расставляет точки возврата (куда выходить) и отправляет в свой аргуменет условную 'команду выхода' в эту точку возврата.
forM_ - запустить монадические вычисления на 'iterable' коллекции, и склеить 'слева направо', выкидывая результат. Он получает здесь лямбду, в которую передает элемент. Эта внутренняя лямбда синтаксически захватывает 'команды выхода' из более внешних.
Если тебя смущает $, то это чтоб скобки не размножались. f $ g == f (g) . Удобно, когда нужно отграничить лямбду или сделать длинный пайплайн.
no subject
Date: 2024-05-24 04:27 pm (UTC)Семантика цикла в верхнем примере — поиск с ранним выходом при успехе и ранним осознанием облома. Соответственно, его надо выражать не в базисе map/filter, а в базисе map/filter/take 1.
Не тестировал, но что-то такое:
no subject
Date: 2024-05-27 09:23 am (UTC)no subject
Date: 2024-05-24 12:30 pm (UTC)Не обязательно к хаскелю, э. Скала тоже хорошая.
no subject
Date: 2024-05-24 01:31 pm (UTC)no subject
Date: 2024-05-24 01:56 pm (UTC)Ну где-то да. At a certain degree.