Skip to content

Commit

Permalink
Merge pull request #4 from paluh/omap-index-based-operations
Browse files Browse the repository at this point in the history
Add index based OMap operations
  • Loading branch information
paluh authored Dec 15, 2021
2 parents 2d4c6fa + 1613071 commit 2dd8b95
Show file tree
Hide file tree
Showing 3 changed files with 63 additions and 0 deletions.
27 changes: 27 additions & 0 deletions src/Data/Map/Ordered/OMap.purs
Original file line number Diff line number Diff line change
Expand Up @@ -5,9 +5,14 @@ module Data.Map.Ordered.OMap
, fromFoldable
, fromFoldableWithIndex
, insert
, insertAt
, isEmpty
, keys
, keyIndex
, lookup
, moveLeft
, moveRight
, moveTo
, singleton
, toUnfoldable
, unionWith
Expand Down Expand Up @@ -137,6 +142,15 @@ insert k v (OMap m) =
unit
) -- Anonymous function wrapper added to delay computation of the default case

keyIndex :: forall k v. Eq k => k -> OMap k v -> Maybe Int
keyIndex k (OMap m) = Array.findIndex (eq k <<< fst) m

insertAt :: forall k v. Ord k => Int -> k -> v -> OMap k v -> Maybe (OMap k v)
insertAt i k v m = do
let
OMap m' = delete k m
OMap <$> Array.insertAt i (k /\ v) m'

delete :: forall k v. Ord k => k -> OMap k v -> OMap k v
delete k om = filterKeys ((/=) k) om

Expand All @@ -152,3 +166,16 @@ alter f k om = case mOldValue, mNewValue of
mOldValue = lookup k om

mNewValue = f mOldValue

moveTo :: forall k v. Ord k => Int -> k -> OMap k v -> Maybe (OMap k v)
moveTo i k m = do
v <- lookup k m
let
m' = delete k m
insertAt i k v m'

moveLeft :: forall k v. Ord k => k -> OMap k v -> Maybe (OMap k v)
moveLeft k m = keyIndex k m >>= \i -> moveTo (i - 1) k m

moveRight :: forall k v. Ord k => k -> OMap k v -> Maybe (OMap k v)
moveRight k m = keyIndex k m >>= \i -> moveTo (i + 1) k m
34 changes: 34 additions & 0 deletions test/Data/Map/Ordered.purs
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
module Data.Map.Ordered.Spec
( orderedMapSpec
) where

import Prelude

import Data.Map.Ordered.OMap (fromFoldable, moveLeft, moveRight)
import Data.Maybe (Maybe(..))
import Data.Tuple.Nested ((/\))
import Test.Spec (Spec, describe, it)
import Test.Spec.Assertions (shouldEqual)

orderedMapSpec :: Spec Unit
orderedMapSpec = do
describe "moveLeft" do
it "fails on the first element" do
let
m = fromFoldable [ "foo" /\ 1, "bar" /\ 2, "baz" /\ 3 ]
moveLeft "foo" m `shouldEqual` Nothing
it "moves the second element" do
let
m = fromFoldable [ "foo" /\ 1, "bar" /\ 2, "baz" /\ 3 ]
moveLeft "bar" m `shouldEqual`
(Just $ fromFoldable [ "bar" /\ 2, "foo" /\ 1, "baz" /\ 3 ])
describe "moveRight" do
it "fails on the last element" do
let
m = fromFoldable [ "foo" /\ 1, "bar" /\ 2, "baz" /\ 3 ]
moveRight "baz" m `shouldEqual` Nothing
it "moves the second element" do
let
m = fromFoldable [ "foo" /\ 1, "bar" /\ 2, "baz" /\ 3 ]
moveRight "bar" m `shouldEqual`
(Just $ fromFoldable [ "foo" /\ 1, "baz" /\ 3, "bar" /\ 2 ])
2 changes: 2 additions & 0 deletions test/Main.purs
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ import Data.Array.Extra.Spec (arrayExtraSpec)
import Data.BigInt.Argonaut.Spec (bigIntSpec)
import Data.Cursor.Spec (cursorSpec)
import Data.Foldable.Extra.Spec (foldableExtraSpec)
import Data.Map.Ordered.Spec (orderedMapSpec)
import Data.String.Extra.Spec (stringExtraSpec)
import Effect (Effect)
import Effect.Aff (launchAff_)
Expand All @@ -23,3 +24,4 @@ main =
stringExtraSpec
assocMapSpec
bigIntSpec
orderedMapSpec

0 comments on commit 2dd8b95

Please sign in to comment.