Skip to content

Instantly share code, notes, and snippets.

@lgastako
Last active May 15, 2020 03:53
Show Gist options
  • Save lgastako/8da651c012c4e341e3ca12f22f08833c to your computer and use it in GitHub Desktop.
Save lgastako/8da651c012c4e341e3ca12f22f08833c to your computer and use it in GitHub Desktop.
Numbering nodes in a tree with and without lenses.
module TreeNumbering where
import Control.Lens
import Control.Monad.State
import Data.Tree
tree_ :: Tree Char
tree_ = Node 'd'
[ Node 'b'
[ Node 'a' []
, Node 'c' []
]
, Node 'f'
[ Node 'e' []
, Node 'g' []
]
]
tag :: Traversable t => t a -> t (Int, a)
tag t = evalState (traverse step t) 0
where
step a = do
tag <- postIncrement
pure (tag, a)
postIncrement = do
result <- get
modify succ
pure result
lensTag :: Tree a -> Tree (Int, a)
lensTag = unsafePartsOf each %~ zip [0..]
-- λ> putStrLn . drawTree . fmap show . tag $ tree_
-- (0,'d')
-- |
-- +- (1,'b')
-- | |
-- | +- (2,'a')
-- | |
-- | `- (3,'c')
-- |
-- `- (4,'f')
-- |
-- +- (5,'e')
-- |
-- `- (6,'g')
-- λ> putStrLn . drawTree . fmap show . lensTag $ tree_
-- (0,'d')
-- |
-- +- (1,'b')
-- | |
-- | +- (2,'a')
-- | |
-- | `- (3,'c')
-- |
-- `- (4,'f')
-- |
-- +- (5,'e')
-- |
-- `- (6,'g')
-- λ> tag tree_ == lensTag tree_
-- True
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment