何も

2017-11-21 9 views
1

私はIOモナドで実験だし、これは私が書いたものである:何も

val io: IO[String] = "asdfasdf".pure[IO] 

val i: IO[Unit] = for{ 
    str <- io 
} yield { 
    println(str).pure[IO] 
} 

i.unsafePerformIO() // Performing io ops 

コードが出力を生成しません。次のコードは、正常に動作します。

val io: IO[Unit] = "asdfasdf".pure[IO].flatMap(println(_).pure[IO]) 
io.unsafePerformIO() //prints asdfasdf 

なぜですか?違いはなんですか?あなただけのScalaの持つ巨大な迷惑を打ってきました

答えて

3

Unit

for{ 
    str <- io 
} yield { 
    println(str).pure[IO] 
} 

推察この式はIO[IO[Unit]]ですが、あなたがIO[Unit]を望んでいたこと(値の型を経由して)スカラ座に語ったので、それは基本的に変えてきました式は次のようにこの変換が可能であると思われること

for{ 
    str <- io 
} yield { 
    println(str).pure[IO] // <-- this IO action is basically thrown away 
()     // <-- inserted a Unit return 
} 

さておき...ノートを理由0はAでは不変です。あなたはIOなくListスニペットが戻るの答えに

をコンパイルされません。その場合には、(その型パラメータの共変である) ...

ため IListに置き換えた場合に同じことが起こるでしょう

は代わりに、あなたが書かれている必要があります。

for { 
    str <- io 
    _ <- println(str).pure[IO] 
} 
yield() 

もっとAsides ...

exprは、純粋な表現であり、そしてexprは副作用であるので、私は好むところ私はIO(expr)を使用します。ここで、個人的に私が唯一expr.pure[IO]を使用します。

for { 
    str <- io 
    _ <- IO(println(str)) 
} 
yield() 

そして最後に、これはと等価であることに注意してください:

io >>= IO.putStrLn 
関連する問題