Advertisement
Guest User

Untitled

a guest
Jul 24th, 2017
70
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. -- | Find the first element in a `List` that repeats.
  2. -- It is possible that no element repeats, hence an `Optional` result.
  3. --
  4. -- /Tip:/ Use `findM` and `State` with a @Data.Set#Set@.
  5. --
  6. -- prop> case firstRepeat xs of Empty -> let xs' = hlist xs in nub xs' == xs'; Full x -> length (filter (== x) xs) > 1
  7. -- prop> case firstRepeat xs of Empty -> True; Full x -> let (l, (rx :. rs)) = span (/= x) xs in let (l2, r2) = span (/= x) rs in let l3 = hlist (l ++ (rx :. Nil) ++ l2) in nub l3 == l3
  8. firstRepeat ::
  9.   Ord a =>
  10.   List a
  11.   -> Optional a
  12. firstRepeat list =
  13.   eval (firstRepeatH list) S.empty
  14.  
  15. firstRepeatH ::
  16.   Ord a =>
  17.   List a
  18.   -> State (S.Set a) (Optional a)
  19. firstRepeatH Nil =
  20.   return Empty
  21. firstRepeatH (x:.xs) =
  22.   do
  23.     res <- addH x
  24.     if res == Empty
  25.       then firstRepeatH xs
  26.       else return res
  27.  
  28. addH ::
  29.   Ord a =>
  30.   a
  31.   -> State (S.Set a) (Optional a)
  32. addH a =
  33.   State (\s -> if (S.member a s) then (Full a, s) else (Empty, S.insert a s))
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement