Would it be truthful to say `EqK` is a utility tha...
# arrow
c
Would it be truthful to say
EqK
is a utility that aims to make it possible to use a normal Eq implementation, but on the content of an object rather than the object itself? Eg. If we have
Eq<Car>
, we can use
EqK
to use our
Eq<Car>
in a
List<Car>
? I think that's what the documentation means by ‘lifting', but I'm really not sure.
But if that's the case, I don't understand the difference with `map`: to me
map
was already the ‘let's take something that works on an object, and apply it to the contents of a container' As in,
Copy code
Some("Thing").map {
  Eq.any().run {
    it.eqv("Thing")
  }
}
j
EqK
is sort of like an equality instance for the structure rather than the full data. When we have for example
EqK<ForList>
that means that we can create a
Eq<List<A>>
given an
Eq<A>
instance. It is mostly used to create
Eq
instances for container-like datatypes. In arrow we use it in tests and laws so that we can define laws for higher kinded datatypes without fixing the whole type: For example functor laws take an
EqK<F>
so that the test can decide what
F<A>
it will use for testing (as that should never matter for these laws) These instances are only of use if you want to test for equality on a given higherkinded type
F
without specifying what the full type
F<A>
. This becomes useful if a)
A
is unknown at that callsite, b)
A
does not matter (like in laws for
F
).
The use-case for lifted typeclasses is admittedly narrow, but when you need this type it is irreplaceable ^^ You can define this for almost every typeclass but in arrow we only really had use for
EqK
for now.
c
Would it be fair to say that it's a wrapper to get deep-equality? As in, with a
EqK<List<A>>
, you can check that two
List<A>
are deeply equal?
j
Not really.
EqK<List<A>>
cannot be defined as it expects a higher kinded type which
List<A>
isn't. Maybe this gives some clarity:
List.eq(Int.eq()).run { xs.eqv(ys) } == List.eqK().run { xs.eqK(ys, Int.eq()) }
EqK
is like a "factory" for list equality instances, it lifts ordinary eq instances into list equality instances, nothing more. The only difference between the two is when you give it the inner equality instance. With
eqK
you can defer that.