What is the difference between `ix` and `at` in the Lens library of Haskell -
all know 1 works , other doesn't.
context: have 1 data structure f
contains data.map.map k s
data structure s
. goal build lens
given f
, k
describe field in s
.
the difficulty key k
may not present in map. that's fine function can wrap return in maybe. not propagate lens through maybe using at
. after reading lot of stack overflow answers, came across this one.
it turns out replacing at
ix
solved type problems if replaced (^.)
(^?)
.
question: seems at
, ix
same thing, @ least regard map
. both take key , give 'lens' value @ key. however, ix
seems play nice function composition operator (.)
. difference between two?
off topic rant:
i infix operators as next guy control.lens package seems have gone little overboard. new user having english names , key somewhere lower learning curve. due huge number of wrapper classes used in lens library particularly difficult dig through type signatures if don't know going on. code starting perl heaven sake.
that at
, ix
different noticable if @ available instances classes containing these functions:
- instances of
at
: map, intmap, hashmap - instances of
ixed
: [a], map, bytestring, text, , lot more
all instances if at
instance of ix
, not instances of ix
instance of at
.
so what's difference between them? at
containers allow inserting keys not present in container. possible map, not e.g. list. still able index list , change items there, ix
doesn't allow creating new items, "does nothing" when try write key not there.
>>> data.map.fromlist [('a', 1)] & @ 'b' .~ 4 fromlist [('a',1),('b',4)] -- inserts value >>> data.map.fromlist [('a', 1)] & ix 'b' .~ 4 fromlist [('a',1)] -- nothing because key not present
(there shortcut a .~ b
, a ?~ b
)
technically, difference comes fact ix
traversal whereas at
lens. , because at
lens "returns" maybe something, cannot compose lens takes plain "something". ix
traversal 0 or 1 values, can compose ix other traversal (just can write traverse . traverse
). (^?)
takes first value (head) of traversal.
you can derive ix
at
:
ixat = @ . traverse
the same definition is in lens, except it's using (<.)
composition keep index at. (at
, ix
both indexed lenses / traversals).
off-topic: operators lens have infix names, can find (incomplete) table at: https://github.com/ekmett/lens/wiki/operators
Comments
Post a Comment