indique/elm-pairdict/1.0.0

NOTE: the latest version is 6.0.3

PairDict

type PairDict left right

Want to look up value-pairs from the left or the right?

Example: cased letters

casedLetters=
  empty
  |>insert { left= 'a', right= 'A' }
  |>insert { left= 'b', right= 'B' }
  |>insert { left= 'c', right= 'C' }


upperCase char=
  rightOf char casedLetters
type alias Pair comparableLeft comparableRight =
{ left : comparableLeft
, right : comparableRight
}

left & right as a value-pair

create

empty : PairDict left right

start with an empty PairDict

empty --fromList []
Dict comparableLeft comparableRight
-> PairDict comparableLeft comparableRight

Create a PairDict conveniently from Pair-Tuples. left is the first, right is the second. If right or left values are given multiple times, the value first in the List is prefered.

lowerToUpperLetters=
  Dict.empty
  |>Dict.insert 'a' 'A'
  |>Dict.insert 'b' 'B'


lowerUpperLetters= fromDict lowerToUpperLetters
List ( comparableLeft, comparableRight )
-> PairDict comparableLeft comparableRight

Create a PairDict conveniently from Tuples. left is the first, right is the second. If right or left values are given multiple times, the value first in the List is prefered.

fromList
  [ ( 'b', 'B' ) --+ { left= 'b', right= 'B' }
  , ( 'a', 'A' ) --+ { left= 'a', right= 'A' }
  , ( 'b', 'C' ) --ignored, as the left value already exists
  , ( 'c', 'A' ) --ignored, as the right value already exists
  , ( 'c', 'C' ) --+ { left= 'c', right= 'C' }
  ]

access

comparableLeft
-> PairDict comparableLeft comparableRight
-> Maybe comparableRight

Just the right value if the left value is present in the PairDict, else Nothing

casedLetters=
  empty
  |>insert { left= 'a', right= 'A' }
  |>insert { left= 'b', right= 'B' }


lowerCase char=
  Dict.leftOf char casedLetters
comparableRight
-> PairDict comparableLeft comparableRight
-> Maybe comparableLeft

Just the right value if the left value is present in the PairDict, else Nothing

casedLetters=
  empty
  |>insert { left= 'a', right= 'A' }
  |>insert { left= 'b', right= 'B' }
  |>insert { left= 'c', right= 'C' }


upperCase char=
  rightOf char casedLetters

properties

size : PairDict comparableLeft comparableRight -> Int

How many pairs there are.

size empty --0


size
  (fromList
    (List.range 0 41 |>List.map (\i-> ( i, i )))
  )
--42

in

Pair comparableLeft comparableRight
-> PairDict comparableLeft comparableRight
-> PairDict comparableLeft comparableRight

Put in a left-right-Pair If either value is already present, the dict is unchanged.

empty
|>insert { left= "(", right= ")" }
|>insert { right= "fire", left= "water" }
--fromList
--  [ ( "(", ")" ) ( "water", "fire" ) ]
PairDict comparableLeft comparableRight
-> PairDict comparableLeft comparableRight
-> PairDict comparableLeft comparableRight

Merge 2 PairDicts. If a value on the left or right is present, prefer the second dict.

numberOperatorNames=
  fromList
    [ ( '+', "plus" )
    , ( '-', "minus" )
    ]
boolOperatorNames=
  fromList
    [ ( '∧', "and" )
    , ( '∨', "or" )
    ]
operatorNames=
  union numberOperatorNames boolOperatorNames

out

comparableLeft
-> PairDict comparableLeft comparableRight
-> PairDict comparableLeft comparableRight

remove left-right pair. If left does not exist, the PairDict is unchanged

empty
|>insert "(" ")"
|>removeLeft "("
--empty
comparableRight
-> PairDict comparableLeft comparableRight
-> PairDict comparableLeft comparableRight

remove left-right pair. If right does not exist, the PairDict is unchanged

empty
|>insert "(" ")"
|>removeRight ")"
--empty

transform

lefts : PairDict left right -> List left

values on the left

brackets=
  fromList [ ( '(', ')' ), ( '{', '}' ) ]
opening= lefts brackets
rights : PairDict left right -> List right

values on the right

brackets=
  fromList [ ( '(', ')' ), ( '{', '}' ) ]
closing= rights brackets
swapLeftRight : PairDict left right -> PairDict right left

What has been left → right, right → left.

upperToLower=
  fromList
    [ ( 'A', 'a' ), ( 'B', 'b' ) ]
lowerToUpper=
  upperToLower |>swapLeftRight
(Pair comparableLeft comparableRight -> result -> result)
-> result
-> PairDict comparableLeft comparableRight
-> result

Reduce the left-right Pairs from highest left to lowest left

brackets=
  fromList
    [ ( '(', ')' )
    , ( '{', '}' )
    ]
openingAndClosing=
  foldl
    (\{ left, right } acc->
      String.fromList [ left, right ]
    )
    []
  --[ "{}", "()" ]
(Pair comparableLeft comparableRight -> result -> result)
-> result
-> PairDict comparableLeft comparableRight
-> result

Reduce the left-right Pairs from lowest left to highest left

brackets=
  fromList
    [ ( '(', ')' )
    , ( '{', '}' )
    ]
openingAndClosing=
  brackets
  |>foldl
      (\{ left, right } acc->
        acc ++[ String.fromList [ left, right ] ]
      )
      []
  --[ "()", "{}" ]
map :
( Pair comparableLeft comparableRight
-> Pair comparableResultLeft comparableResultRight
)
-> PairDict comparableLeft comparableRight
-> PairDict comparableResultLeft comparableResultRight

map pairs

digitNames=
  fromList
    [ ( 0, "zero" )
    , ( 1, "one" )
    ]
mathSymbolNames=
  digitNames
  |>map
      (\{left,right}->
        { left= String.fromInt left
        , right= right
        }
      )
  |>insert { left= "+", right= "plus" }
toDict : PairDict left right -> Dict left right

convert to a Dict, which you can access only from the left

casedLetters=
  fromList
    [ ( 'A', 'a' ), ( 'B', 'b' ) ]
lowerFromUpper=
  casedLetters |>toDict