packages feed

axel-0.0.11: src/Axel/Utils/Tuple.hs

module Axel.Utils.Tuple where

import Axel.Prelude

import Control.Lens.Operators ((^.))
import Control.Lens.Tuple (_1, _2)
import Control.Lens.Type (Lens)

type Annotated ann a = (a, ann)

annotate :: ann -> a -> Annotated ann a
annotate = flip (,)

annotateWith :: (a -> ann) -> a -> Annotated ann a
annotateWith f x = annotate (f x) x

unannotated :: Lens (Annotated ann a) (Annotated ann a') a a'
unannotated = _1

annotation :: Lens (Annotated ann a) (Annotated ann' a) ann ann'
annotation = _2

unannotate :: Annotated ann a -> a
unannotate = (^. unannotated)

flattenAnnotations ::
     Annotated ann (Annotated ann' a) -> Annotated (ann', ann) a
flattenAnnotations x =
  let outerAnnotation = x ^. annotation
      innerAnnotation = unannotate x ^. annotation
      innerValue = unannotate $ unannotate x
   in annotate (innerAnnotation, outerAnnotation) innerValue