extrapolate-0.2.1: src/Test/Extrapolate/Utils.hs
-- |
-- Module : Test.Extrapolate.Utils
-- Copyright : (c) 2017 Rudy Matela
-- License : 3-Clause BSD (see the file LICENSE)
-- Maintainer : Rudy Matela <rudy@matela.com.br>
--
-- This module is part of Extrapolate,
-- a library for generalization of counter-examples.
--
-- Misc. utilities.
module Test.Extrapolate.Utils
( (+++)
, nubMerge
, nubMergeOn
, nubMergeBy
, foldr0
, fromLeft
, fromRight
, elemBy
)
where
import Data.Function (on)
nubMergeBy :: (a -> a -> Ordering) -> [a] -> [a] -> [a]
nubMergeBy cmp (x:xs) (y:ys) = case x `cmp` y of
LT -> x:nubMergeBy cmp xs (y:ys)
GT -> y:nubMergeBy cmp (x:xs) ys
EQ -> x:nubMergeBy cmp xs ys
nubMergeBy _ xs ys = xs ++ ys
nubMergeOn :: Ord b => (a -> b) -> [a] -> [a] -> [a]
nubMergeOn f = nubMergeBy (compare `on` f)
nubMerge :: Ord a => [a] -> [a] -> [a]
nubMerge = nubMergeBy compare
(+++) :: Ord a => [a] -> [a] -> [a]
(+++) = nubMerge
infixr 5 +++
-- variation of foldr that only uses "zero" when the list is empty
foldr0 :: (a -> a -> a) -> a -> [a] -> a
foldr0 f z xs | null xs = z
| otherwise = foldr1 f xs
-- note these versions of fromLeft and fromRight differ from the ones of
-- Data.Either since 4.10.0.0.
fromLeft :: Either a b -> a
fromLeft (Left x) = x
fromLeft _ = error "fromLeft: not a left"
fromRight :: Either a b -> b
fromRight (Right x) = x
fromRight _ = error "fromRight: not a right"
elemBy :: (a -> a -> Bool) -> a -> [a] -> Bool
elemBy (==) x = any (== x)