On 10/04/12 09:55, Arnaud Bailly wrote:
Hello,
I am manipulating labeled multiway trees, some kind of "lightweight"
XML notation. One thing I would like to be able to do is manipulating
a tree as a list of (Path, Value). Generating such a list is easy but
I am a little bit surprised to find it harder to reconstruct a tree,
given such a list assuming some sensible properties (list is ordered,
for example).

I got the intuition this has already been tackled in one way or
another in a functional setting in Haskell (I code in Java but using
mostly functional constructs), but don't know where to look.


The haskell solution would be to consider first how to turn a single (Path,Value) into a tree. Then you just combine these trees for all the paths by taking their union. I attached some code.



Twan
import qualified Data.Map as Map
import Data.Map (Map)

data Tree a b = Leaf b | Branch (Map a (Tree a b))
type Path a = [a]

fromTree :: Tree a b -> [(Path a,b)]
fromTree (Leaf x) = [([],x)]
fromTree (Branch xs) = [ (a:p,x) | (a,t) <- Map.toList xs, (p,x) <- fromTree t ]

toTree :: Ord a => [(Path a,b)] -> Tree a b
toTree = foldr unionTree emptyTree . map (uncurry toTree1)

toTree1 :: Ord a => Path a -> b -> Tree a b
toTree1 [] b = Leaf b
toTree1 (x:xs) b = Branch (Map.singleton x (toTree1 xs b))

emptyTree :: Tree a b
emptyTree = Branch Map.empty

unionTree :: Ord a => Tree a b -> Tree a b -> Tree a b
unionTree (Branch xs) y | Map.null xs = y
unionTree x (Branch ys) | Map.null ys = x
unionTree (Branch xs) (Branch ys) = Branch (Map.unionWith unionTree xs ys)
unionTree _ _ = error "Can't have a leaf on the same level as something else"

_______________________________________________
Haskell-Cafe mailing list
[email protected]
http://www.haskell.org/mailman/listinfo/haskell-cafe

Reply via email to