Haskell ã®ãªã¹ãã¯ã¢ããã§ãããããã¯é決å®æ§ã®æèã表ãã¨è¨ããã¾ãããããããã®ãã¨ãæ±ã£ãä¾é¡ã¯å°ãªãã¦ããããã¤ãã¤ãã§ãããããã§ãScheme ã§æ¸ãããããä¾é¡ã Haskell ã§æ¸ãç´ãã¦ã¿ã¾ããã
ãOn Lispãã®ãé決å®æ§ãã®ç« ã§ã¯ãè¬ãããé¢æ° choose 㨠fail ãåºã¦ãã¾ãããããªé£ãã話ãããªãã¦ããHaskell ã§ã¯åã«å ¨æ¢ç´¢ãããã¨ã§é決å®æ§ãå®ç¾ã§ãã¾ãããªããªããHaskell ã®è©ä¾¡æ¦ç¥ã¯é 延è©ä¾¡ãªã®ã§ãçãã®å é ããè¦æ±ããªããã°ãæ®ãã®çãã¯æ¢ããªãããã§ãã
ã¨ããããã§ãHaskell ã§é決å®æ§ã®åé¡ã解ããã¨ã¯ããªã¹ãã使ã£ã¦æ®éã«ããã°ã©ãã³ã°ãããã¨ã¨ãªããå¤ããã¾ããã
ä¸å¹³æ¹ã®å®ç
ãもうひとつの Scheme 入門ãã«è¼ã£ã¦ããä¸å¹³æ¹ã®å®çã«é¢ããåé¡ã解ãã¦ã¿ã¾ãããã
x = [1,2,3,4,5], y = [3,4,5,6,7], z = [4,5,6,8,9] ã®ã¨ããx^2+y^2=z^2 ãæºããæ´æ°ã®çµ (x,y,z) ãæ±ããªããã
ãªã¹ãå å 表è¨ã使ãã°ãç°¡åã§ããã
[(x,y,z)| x <- [1,2,3,4,5], y <- [3,4,5,6,7], z <- [4,5,6,8,9], x^2 + y^2 == z^2] â [(3,4,5),(4,3,5)]
çµè·¯æ¢ç´¢
次ã«ããお気楽 Scheme プログラミング入門ãã«è¼ã£ã¦ããçµè·¯æ¢ç´¢ã®åé¡ã解ãã¦ã¿ã¾ãã
以ä¸ã®ãããã¯ã¼ã¯ã«ããã¦ãA ãã F ã¸ã®çµè·¯ãè¦ã¤ããªããã
A -- B -- D \ | | \ \ | | \ C -- E -- F
å®è£ ãæå¾ã«ç¤ºãã¾ããçµè·¯æ¢ç´¢ãããé¢æ°ã pathFind ã§ããããã¯ã¼ã¯ã®æ å ±ãã´ã¼ã«ãããã¦ç¾æç¹ã§ã®çµè·¯ãä»£å ¥ããã¨ãã´ã¼ã«ã«è³ãã¾ã§ã®ãã¹ã¦ã®çµè·¯ãæ¢ãã¾ãã
pathFind network F (S.singleton A) â [fromList [A,B,C,E,D,F],fromList [A,B,C,E,F],fromList [A,B,D,E,F],fromList [A,B,D,F],fromList [A,C,B,D,E,F],fromList [A,C,B,D,F],fromList [A,C,E,D,F],fromList [A,C,E,F]]
pathFind ã¯ããªã¹ãã«å¯¾ã㦠do ãç¨ãã¦ãã¾ãããããé決å®æ§ãå®ç¾ããæ ¸å¿ã§ãã
以ä¸ã®ã³ã¼ãã§ã¯ãæ¬å½ã«ãªã¹ãã§ããå¿ è¦ãããé¨åã«ã ããªã¹ããç¨ãã¦ãã¾ããåãããè¦ã¦ä¸ãããã
import Control.Monad import Data.Maybe import qualified Data.Map as M import qualified Data.Sequence as S data Node = A | B | C | D | E | F deriving (Eq, Ord, Show) type Network = M.Map Node [Node] network :: Network network = M.fromList [ (A, [B, C]) , (B, [A, C, D]) , (C, [A, B, E]) , (D, [B, E, F]) , (E, [C, D, F]) , (F, [E]) ] neighbors :: Node -> Network -> [Node] neighbors n g = fromJust $ M.lookup n g noLoop :: Node -> S.Seq Node -> Bool noLoop x sq = isNothing $ S.elemIndexL x sq addTo :: Node -> S.Seq Node -> S.Seq Node addTo = flip (S.|>) currentNode :: S.Seq Node -> Node currentNode path = case S.viewr path of _ S.:> x -> x _ -> error "currentNode" pathFind :: Network -> Node -> S.Seq Node -> [S.Seq Node] pathFind net goal path = do x <- neighbors (currentNode path) net guard $ noLoop x path let path' = x `addTo` path if x == goal then return path' else pathFind net goal path'