2017-10-19 5 views
3

このプログラムを考えてみましょ遅延評価の問題:イドリス -

module test 

import Effects 
import Effect.StdIO 

(>>==) : Maybe a -> Lazy (a -> Maybe b) -> Maybe b 
(>>==) Nothing (Delay map) = Nothing 
(>>==) (Just x) (Delay map) = map x 

nothing : String -> Eff (Maybe String) [STDIO] 
nothing s = do 
    putStrLn s 
    pure Nothing 

func : Maybe String -> String -> Maybe String 
func Nothing _ = Nothing 
func (Just s) t = Just (s ++ t) 

test : Eff() [STDIO] 
test = do 
    let m = !(nothing "a") >>== (func !(nothing "b")) 
    putStrLn "end" 

main : IO() 
main = run test 

>>==の右手側は怠惰で宣言して!(nothing "a")リターンNothingされているので、私は>>==の右手側は評価されないだろうと予想されます。

しかし、実際には、評価を受けるん、と私は理由を理解することはできません...私は最初Nothing

を得るとき

より広く、私は多分返すEff計算を連結し、実行を停止しようとしています

答えて

0

Desugar the!表記

test = do 
    x <- nothing "a" 
    y <- nothing "b" 
    let m = x >>== (func y) 
    putStrLn "end" 

は、明らかに "A"、 "B"、および "終了" が全て印刷されるが、funcが評価されなくてもよいです。

Maybeに直接ではなく>>==を定義して、(一部)Effの値にする必要があると思います。

HTHは

+0

私が実際に希望することは計算が '「b」は、'印刷されないこと「」 '、'ので、何も後に停止することです。私は 'do'表記が間違った文脈、すなわち' Maybe'の代わりに 'Eff'で働いているので、これは起こらないと思います。ハスケルでは、私は 'MaybeT'モナドトランスを使ってこの問題に取り組んでいますが、Idrisに類似したものがありますか?従属型は私に何かクリーナーをさせることができるのですか? – marcosh

+0

'EXCEPTION()'エフェクトを追加します。 '何も' 'raise()'を呼び出すと、あなたが何を持っていても動作する定義済みのハンドラがすでにあります。 –

関連する問題