As seen here, map is defined
in a slightly funky way
For completeness' sake, here's the code:
implicit def FunctionFunctor[R] = new Functor[({type l[a] = R=>a})#l] {
def map[A, B](fa: R => A)(f: A => B) : R => B = (x => f(fa(x)))
}
More concretely - new Functor[({type l[a] = R=>a})#l]
I do think I know what's going on, but can't say honestly that I fully understand the concept. And since there is no any hint, I can't event google the term (I simply don't know that to google). Does some tutorial (or review, or whatever) exist where this is explained with a better level of detalization? I'd appreciate even more is someone could explain it right here in the answers.
In structural typing, an element is considered to be compatible with another if, for each feature within the second element's type, a corresponding and identical feature exists in the first element's type. Some languages may differ on the details, such as whether the features must match in name.
TypeScript is a Structural Type System. A structural type system means that when comparing types, TypeScript only takes into account the members on the type. This is in contrast to nominal type systems, where you could create two types but could not assign them to each other.
Languages like C++, Java, and Swift have primarily nominal type systems.
Gettings Our Ducks in a Row Fortunately, Scala allows us to write idiomatic code to achieve the same results as duck typing.
This is a special case of structural typing but called a 'type lambda', if you search for type lambda scala
google will give you some results.
In short, it's used in a similar fashion as partially applied functions.
def x(a:Int, b:Int):Int = a * b
val x10 = x(10, _:Int)
x10(2) // 2
An example with types.
type IntEither[B] = Either[Int, B]
val y:IntEither[String] // Either[Int, String]
In some cases methods or classes expect a type with a single parameter
class Test[F[_]]
You can not give the Test
class an Either
because Test
expects a type with 1 parameter and Either
has 2. In order to be able to pass in an Either
we can partially apply it
type X[B] = Either[Int, B]
new Test[X]
An alternative way of writing it is like this:
type X = {
type T[x] = Either[Int, x]
}
new Test[X#T]
Instead of creating a type alias, we can also define the X
type anonymously
new Test[({type T[x] = Either[Int, x]})#T]
These all give you an instance of type Test[Either[Int, x]]
.
Edit
Your example could look like this:
type PartiallyTypedFunction[R] = {
type T[x] = R => x
}
implicit def FunctionFunctor[R] =
new Functor[PartiallyTypedFunction[R]#T] {
def map[A, B](fa: R => A)(f: A => B): R => B = (x => f(fa(x)))
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With