... or mishaps of a Haskell programmer that has to code Scala, part 5.
I have the following structure in Scala:
case class ResourceTree(
resources: Map[String, ResourceTree]
)
And, using Cats, I would like to define a Semigroup
instance of it.
object ResourceTreeInstances {
implicit val semigroupInstance = new Semigroup[ResourceTree] {
override def combine(x: ResourceTree, y: ResourceTree): ResourceTree = {
ResourceTree(
x.resources |+| y.resources
)
}
}
This will result in the following error:
value |+| is not a member of Map[String, ResourceTree]
[error] Note: implicit value semigroupInstance is not applicable here because it comes after the application point and it lacks an explicit result type
[error] x.resources |+| y.resource
So, my guess was that since I'm defining the instance for Semigroup
the Scala compiler cannot derive an instance for Semigroup
of Map[String, ResourceTree]
. This seems to be confirmed, since the following instance is compiles:
implicit val semigroupInstance = new Semigroup[ResourceTree] {
override def combine(x: ResourceTree, y: ResourceTree): ResourceTree = {
dummyCombine(x, y)
}
}
// FIXME: see if there's a better way to avoid the "no instance of Semigroup" problem
def dummyCombine(x: ResourceTree, y: ResourceTree): ResourceTree = {
ResourceTree(
x.resources |+| y.resources
)
}
I'm really hoping I'm wrong because if this is the right way of defining an instance for a Semigroup in Scala I'll start considering the idea of giving up doing FP in this language.
Is there a better way?