{"action":"created","issue":{"url":"https://api.github.com/repos/purescript/purescript-prelude/issues/20","repository_url":"https://api.github.com/repos/purescript/purescript-prelude","labels_url":"https://api.github.com/repos/purescript/purescript-prelude/issues/20/labels{/name}","comments_url":"https://api.github.com/repos/purescript/purescript-prelude/issues/20/comments","events_url":"https://api.github.com/repos/purescript/purescript-prelude/issues/20/events","html_url":"https://github.com/purescript/purescript-prelude/issues/20","id":72717240,"number":20,"title":"Possible functions.","user":{"login":"joneshf","id":1356417,"avatar_url":"https://avatars.githubusercontent.com/u/1356417?v=3","gravatar_id":"","url":"https://api.github.com/users/joneshf","html_url":"https://github.com/joneshf","followers_url":"https://api.github.com/users/joneshf/followers","following_url":"https://api.github.com/users/joneshf/following{/other_user}","gists_url":"https://api.github.com/users/joneshf/gists{/gist_id}","starred_url":"https://api.github.com/users/joneshf/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/joneshf/subscriptions","organizations_url":"https://api.github.com/users/joneshf/orgs","repos_url":"https://api.github.com/users/joneshf/repos","events_url":"https://api.github.com/users/joneshf/events{/privacy}","received_events_url":"https://api.github.com/users/joneshf/received_events","type":"User","site_admin":false},"labels":[],"state":"closed","locked":false,"assignee":null,"milestone":null,"comments":4,"created_at":"2015-05-02T23:31:30Z","updated_at":"2016-03-29T03:49:42Z","closed_at":"2016-03-29T03:49:42Z","body":"How about some additional functions? Some are things I've used in the past, some are others I thought were sort of interesting, but might not be useful. Feel free to reject all of them.\r\n\r\n### Eq stuff\r\n\r\n```purescript\r\nequaling :: forall b. (Eq b) => (a -> b) -> a -> a -> Boolean\r\nequaling = on eq\r\n```\r\n\r\nUseful for things like `intersectBy` or `nubBy`.\r\n\r\nCould also use a newtype to change the value of equality.\r\n\r\n```purescript\r\nnewtype Diff a = Diff a\r\n\r\ninstance (Eq a) => Eq (Diff a) where\r\n  (==) (Diff x) (Diff y) = x /= y\r\n```\r\n\r\n### Ord stuff\r\n```purescript\r\nascending :: forall a b. (Ord b) => (a -> b) -> a -> a -> Ordering\r\nascending = on compare\r\n\r\nclamp :: forall a. (Ord a) => a -> a -> a -> a\r\nclamp low high x = max low (min high x)\r\n\r\nclamped :: forall a. (Ord a) => a -> a -> a -> Boolean\r\nclamped low high x = low <= x && x <= high\r\n\r\ndescending :: forall a b. (Ord b) => (a -> b) -> a -> a -> Ordering\r\ndescending = on (flip compare)\r\n\r\nmax :: forall a. (Ord a) => a -> a -> a\r\nmax x y = if x <= y then y else x\r\n\r\nmin :: forall a. (Ord a) => a -> a -> a\r\nmin x y = if x <= y then x else y\r\n```\r\n\r\n`ascending` and `descending` are helpful for when you use something like `sortBy`. Also could use a newtype for changing the order of things, ala haskell:\r\n\r\n```purescript\r\nnewtype Desc a = Desc a\r\n\r\ninstance eqDesc :: (Eq a) => Eq (Desc a) where\r\n  (==) (Desc x) (Desc y) = x == y\r\n\r\ninstance ordDesc :: (Ord a) => Ord (Desc a) where\r\n  compare (Desc x) (Desc y) = compare y x\r\n```\r\n\r\n### Semiring stuff\r\n```purescript\r\ninc :: forall a. (Semiring a) => a -> a\r\ninc = add one\r\n```\r\n\r\n### Ring stuff\r\n```purescript\r\nabs :: forall a. (Ord a, Ring a) => a -> a\r\nabs x = if x <= zero then negate x else x\r\n\r\ndec :: forall a. (Ring a) => a -> a\r\ndec = flip sub one\r\n\r\nsigNum :: forall a. (Ord a, ModuloSemiring a) => a -> a\r\nsigNum x\r\n  | x == zero = zero \r\n  | otherwise =  x `div` abs x\r\n```"},"comment":{"url":"https://api.github.com/repos/purescript/purescript-prelude/issues/comments/202696244","html_url":"https://github.com/purescript/purescript-prelude/issues/20#issuecomment-202696244","issue_url":"https://api.github.com/repos/purescript/purescript-prelude/issues/20","id":202696244,"user":{"login":"joneshf","id":1356417,"avatar_url":"https://avatars.githubusercontent.com/u/1356417?v=3","gravatar_id":"","url":"https://api.github.com/users/joneshf","html_url":"https://github.com/joneshf","followers_url":"https://api.github.com/users/joneshf/followers","following_url":"https://api.github.com/users/joneshf/following{/other_user}","gists_url":"https://api.github.com/users/joneshf/gists{/gist_id}","starred_url":"https://api.github.com/users/joneshf/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/joneshf/subscriptions","organizations_url":"https://api.github.com/users/joneshf/orgs","repos_url":"https://api.github.com/users/joneshf/repos","events_url":"https://api.github.com/users/joneshf/events{/privacy}","received_events_url":"https://api.github.com/users/joneshf/received_events","type":"User","site_admin":false},"created_at":"2016-03-29T03:49:42Z","updated_at":"2016-03-29T03:49:42Z","body":"Yeah. Most of this stuff can be implemented better with https://pursuit.purescript.org/packages/purescript-contravariant/0.2.3"}}