compdata-0.8.1.3: src/Data/Comp/Multi/Number.hs
{-# LANGUAGE TypeOperators #-}
--------------------------------------------------------------------------------
-- |
-- Module : Data.Comp.Multi.Number
-- Copyright : (c) 2012 Patrick Bahr
-- License : BSD3
-- Maintainer : Patrick Bahr <paba@diku.dk>
-- Stability : experimental
-- Portability : non-portable (GHC Extensions)
--
-- This module provides functionality to number the components of a
-- functorial value with consecutive integers.
--
--------------------------------------------------------------------------------
module Data.Comp.Multi.Number
( Numbered (..)
, unNumbered
, number
, HTraversable ()) where
import Data.Comp.Multi.Equality
import Data.Comp.Multi.HFunctor
import Data.Comp.Multi.HTraversable
import Data.Comp.Multi.Ordering
import Control.Monad.State
-- | This type is used for numbering components of a functorial value.
newtype Numbered a i = Numbered (Int, a i)
unNumbered :: Numbered a :-> a
unNumbered (Numbered (_, x)) = x
instance KEq (Numbered a) where
keq (Numbered (i,_)) (Numbered (j,_)) = i == j
instance KOrd (Numbered a) where
kcompare (Numbered (i,_)) (Numbered (j,_)) = i `compare` j
-- | This function numbers the components of the given functorial
-- value with consecutive integers starting at 0.
number :: HTraversable f => f a :-> f (Numbered a)
number x = evalState (hmapM run x) 0 where
run b = do n <- get
put (n+1)
return $ Numbered (n,b)