5

次の有効な Haskell コードを検討してください

module Main where

main :: IO ()
main = do
  let x = f
  print x

f :: Maybe (Int, Int)
f =
  Just 3 >>= (\a ->
    Just 5 >>= (\b ->
      return (a, b)))

関数は、fこのようなdo表記で同等に書き換えることができます

f :: Maybe (Int, Int)
f = do
  a <- Just 3
  b <- Just 5
  return (a, b)

私を悩ませているのは、fインラインの内容を入れると do 表記が機能しないことです。次のコードは解析さえしません。

main :: IO ()
main = do
  let x = do
    a <- Just 3
    b <- Just 5
    return (a, b)
  print x

内部letで頼らざるを得ないというのは正しい(>>=)ですか?

私が取り組んでいる間、次のコードも解析されません。

module Main where

main :: IO ()
main = do
  let x =
    Just 3 >>= (\a ->
      Just 5 >>= (\b ->
        return (a, b)))
  print x

の不必要な制限された力以外に明らかな理由は見当たりませんletbind内部で使用するエレガントな方法はありletますか?

4

1 に答える 1

8

内部letで頼らざるを得ないというのは正しい(>>=)ですか?

いいえ:

main :: IO ()
main = do
  let x = do
      a <- Just 3
      b <- Just 5
      return (a, b)
  print x

Haskell のレイアウトルールでは、バインディングの本体は、e少なくとも(一度に複数を使用している場合は最初のバインディング)p = eの先頭と同じくらい意図されている必要があります。はと (ほぼ) 同じルールに従っているpため、次の関数でこれを確認できます。letdolet … in

f :: Int
f = 
  let x =
    3 + 5
  in x

3 + 5は と同じかそれ以上のインデント レベルを持っていないため、これは機能しませんx。でも、

f :: Int
f =
  let x =
       3 + 5
  in x

動作します。また、上記は機能しますが、それは実際にはそれをmain伝えておらず、のブロックに含まれているため、もう少しインデントする方が良いでしょう:abxdo

main :: IO ()
main = do
  let x = do
        a <- Just 3
        b <- Just 5
        return (a, b)
  print x
于 2015-11-27T18:42:07.680 に答える