Last active
December 18, 2015 06:08
-
-
Save techtangents/5737508 to your computer and use it in GitHub Desktop.
RE: benkolera: Even though it makes your DSL shiny-ish, overloading functions is a PitA to a FP library user. Please use a sum type instead. #bad #scala etorreborre: @benkolera I'm clearly guilty of this but I don't quite get why it is so bad. Pointers?
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Let's use Scala as the implementation language. | |
Say you have an API function setFoo, that is overloaded for Chook and Dog. | |
One might call it either of these ways: | |
setFoo(chook) | |
setFoo(dog) | |
As an API user, I wish to call this function from another function | |
def q(c: Chook) { | |
somefn() | |
setFoo(c) | |
} | |
But, what if this function doesn't know whether it wants to set a Chook or a Dog? | |
I either have to overload or sum-type and switch. | |
e.g. 1 | |
def q(c: Chook) { | |
somefn() | |
setFoo(c) | |
} | |
def q(d: Dog) { | |
somefn() | |
setFoo(d) | |
} | |
e.g. 2 | |
sealed trait ChookOrDog | |
case class IsChook(c: Chook) extends ChookOrDog | |
case class IsDog(d: Dog) extends ChookOrDog | |
def q(cd: ChookOrDog) { | |
somefn() | |
cd match { | |
case IsChook(c) => setFoo(c) | |
case IsDog(d) => setFoo(d) | |
} | |
} | |
And... since setFoo is overloaded, each overload has to handle the separate cases of Chook and Dog somehow. | |
It may end up looking very much like 'q' in example 2, or the Chook or Dog classes would have a common | |
trait that it would use. In the first case you would be using a sum type internally anyway, so you might | |
as well take the sum type as a parameter. In the second case, you are making use of the trait to convert | |
the input type to something else - as such, you should just accept the trait type directly (using | |
inheritance), or as an implicit (typeclass instance). | |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment