module Data.Homeomorphic.ShellId(
ShellIds, ShellId(..), empty, retrieve
) where
import qualified Data.Map as Map
import Data.List
import Data.Homeomorphic.Internal
data ShellId = ShellId {allId :: Int, headId :: Int, restId :: [ShellId]}
data ShellIds k = ShellIds
(Map.Map (Shell k) ShellId)
(Map.Map (k,Int) Int)
empty :: ShellIds k
empty = ShellIds Map.empty Map.empty
retrieve :: Ord k => Shell k -> ShellIds k -> (ShellIds k, ShellId)
retrieve x@(Shell a b c) o@(ShellIds mAll mHead) =
case Map.lookup x mAll of
Just y -> (o, y)
Nothing -> (ShellIds mAll3 mHead3, rAll)
where
(ShellIds mAll2 mHead2, cs) = mapAccumL (flip retrieve) o c
(mHead3, rHead) = retrieveHead (a,b) mHead2
rAll = ShellId (Map.size mAll2) rHead cs
mAll3 = Map.insert x rAll mAll2
retrieveHead :: Ord k => (k,Int) -> Map.Map (k,Int) Int -> (Map.Map (k,Int) Int, Int)
retrieveHead x m =
case Map.lookup x m of
Just y -> (m, y)
Nothing -> (Map.insert x r m, r)
where r = Map.size m