Haskellやっぱ難しいよ。難しいって。
非決定性計算を見た。
Schemeで出てきたんだけどググったらHaskellの例があったので、見てみた。
*SICPのambのあたりで
import Control.Monad solve = do baker <- [1, 2, 3, 4, 5] cooper <- [1, 2, 3, 4, 5] fletcher <- [1, 2, 3, 4, 5] miller <- [1, 2, 3, 4, 5] smith <- [1, 2, 3, 4, 5] guard $ distinct [baker, cooper, fletcher, miller, smith] guard $ baker /= 5 guard $ cooper /= 1 guard $ fletcher /= 1 && fletcher /= 5 guard $ miller > cooper guard $ abs (smith - fletcher) /= 1 guard $ abs (fletcher - cooper) /= 1 [baker, cooper, fletcher, miller, smith] distinct :: Eq a => [a] -> Bool distinct [] = True distinct (x:xs) = all (/=x) xs && distinct xs main :: IO() main = print solve
実行結果: [3,2,4,5,1]
↑こんなの。
すげぇ。条件だけ並べたら結果が返ってきてる。
宣言的だ。すげぇ。
でもなんで結果がでるのかさっぱり分からない。
非決定性計算ってなんだ??まずそこが分からない。
しょうがないよね。文系だもの。(いいわけ)
調べる調べる。
ふむ。非決定性計算って総当りなのか。
とりあえず、コードの断片が分からなければ理解も進むわけがない。
たぶんリストモナドとguardとMonadPlusが分かれば理解できるんじゃなかろうか??
と思って、調べる。
Listモナドの>>=はconcatMapらしい。
いかん。concatMapってなんだ??
:t concatMap
っと。
concatMap :: (a -> [b]) -> [a] -> [b]
なのか。
・・・アカン。do記法ってどうなってるのかわからん。
そこからやるのか・・・。
えーと・・・。
import Control.Monad.List f1 = do a <- [1,2,3] b <- [4,5] [(a,b)]
ってあったとして。
>|haskell||
Main> [1,2,3] >>= (\a -> [4,5] >>= (\b -> [(a,b)]))
[(1,4),(1,5),(2,4),(2,5),(3,4),(3,5)]
Main> [1,2,3] >>= (\a -> concatMap (\b -> [(a,b)]) [4,5])
[(1,4),(1,5),(2,4),(2,5),(3,4),(3,5)]
Main> concatMap (\a -> concatMap (\b -> [(a,b)]) [4,5]) [1,2,3]
[(1,4),(1,5),(2,4),(2,5),(3,4),(3,5)]
Main> :l m.hs
[1 of 1] Compiling Main ( m.hs, interpreted )
Ok, modules loaded: Main.
Main> f1
[(1,4),(1,5),(2,4),(2,5),(3,4),(3,5)]
|