Search code examples
haskelltreeb-tree

Haskell 2-3-4 Tree


We've been asked to create a 2-3-4 tree in Haskell, as in write the data type, the insert function, and a display function.

I'm finding it very difficult to get information on this kind of tree, even in a language I'm comfortable with (Java, C++).

What I have so far -

data Tree t = Empty 
    | Two t (Tree t)(Tree t) 
    | Three t t (Tree t)(Tree t)(Tree t) 
    | Four t t t (Tree t)(Tree t)(Tree t)(Tree t) deriving (Eq, Ord, Show)


leaf2 a = Two a Empty Empty
leaf3 a b = Three a b Empty Empty Empty
leaf4 a b c = Four a b c Empty Empty Empty Empty

addNode::(Ord t) => t ->  Tree t -> Tree t
addNode t Empty = leaf2 t
addNode x (Two t left right)
    | x < t = Two t (addNode x left) right
    | otherwise = Two t left (addNode x right)

This compiles but I'm not sure if it's correct, but not sure how to start writing the insert into a three node or four node.

The assignment also says that "deriving show" for the display function is not enough, that it should print out the tree in the format normally seen in diagrams. Again, unsure on the way to go with this.

Any help or direction appreciated.


Solution

  • I know nothing about 2-3-4 trees, but for the Three node, you would start with something like this:

    addNode t (Three x y left mid right)
      | cond1 = expr1
      | cond2 = expr2
      (etc)
    

    What cond1, cond2, expr1, and expr2 are, exactly, is dependent on the definition of what a 2-3-4 tree is.

    As for a show method, the general outline would be this:

    instance (Show t) => Show (Tree t) where
      show Empty = ...
      show (Two x l r) = ...show x...show l...show r...
      show (Three x y l m r) = ...
      show (Four x y z l m n r) = ...
    

    The implementation depends on how you want it to look, but for the non-Empty cases, you will probably invoke show on all of the components of the tree being shown. If you want to indent the nested parts of the tree, then perhaps you should create a separate method:

    instance (Show t) => Show (Tree t) where
      show = showTree 0
    
    showTree :: Show t => Int -> Tree t -> String
    showTree n = indent . go
      where indent = (replicate n ' ' ++)
            go Empty = "Empty"
            go (Two x l r) = (...show x...showTree (n+1) l...showTree (n+1) r...)
            (etc)