あなたの木はこのように見えると思います...
data Tree a = Leaf a | Branch (Tree a) (Tree a) deriving Show
height
ここで、次の行に沿って再帰関数を定義できます。
height :: Tree a -> Maybe Int
height (Leaf _) = Just 1
height (Branch a b) = ???
2 番目のケース (???) では、サブツリーの高さに 1 を追加しますが、それらが完全であり、同じ高さである場合に限ります。same
サブツリーの高さを取り、サブツリーの高さを含む Maybe Int を返すヘルパー関数 を定義しましょう。
same :: Eq a => Maybe a -> Maybe a -> Maybe a
same (Just a) (Just b) = if a == b then Just a else Nothing
same _ _ = Nothing
これで機能を終了できheight
ます。サブツリーの高さに 1 を追加するだけです。
height :: Tree a -> Maybe Int
height (Leaf _) = Just 1
height (Branch a b) = maybe Nothing (Just . (1+)) subTreeHeight
where subTreeHeight = same (height a) (height b)
で、使い方はこちら。
main :: IO ()
main = do
let aTree = (Leaf 'a')
print aTree
print $ height aTree
let bTree = Branch (Leaf 'a') (Leaf 'b')
print bTree
print $ height bTree
let cTree = Branch (Leaf 'a') (Branch (Leaf 'b') (Leaf 'c'))
print cTree
print $ height cTree
let dTree = Branch (Branch (Leaf 'a') (Leaf 'b')) (Branch (Leaf 'c') (Leaf 'd'))
print dTree
print $ height dTree
これを実行すると、次のようになります。
Leaf 'a'
Just 1
Branch (Leaf 'a') (Leaf 'b')
Just 2
Branch (Leaf 'a') (Branch (Leaf 'b') (Leaf 'c'))
Nothing
Branch (Branch (Leaf 'a') (Leaf 'b')) (Branch (Leaf 'c') (Leaf 'd'))
Just 3