Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Programming with Type Classes

Programming with Type Classes

Typically, object-oriented and functional languages don't have a lot in common. Former usually implement polymorphism through class hierachies and inheritance. Haskell, being a prototypical functional language, offers polymorphism through another mechanism: type classes. This is available in Scala as well! With type classes it becomes surprisingly easy to abstract over completely different classes and methods.

Lars Hupel

April 22, 2013
Tweet

More Decks by Lars Hupel

Other Decks in Programming

Transcript

  1. Patterns Type Classes Use cases Goal var total = 0

    for (doc <- docs) { total += doc.length } total Lars Hupel Programming with Type Classes April 22nd, 2013 2 / 27
  2. Patterns Type Classes Use cases Goal var total = 0

    docs.foreach(doc => total += doc.length) total Lars Hupel Programming with Type Classes April 22nd, 2013 2 / 27
  3. Patterns Type Classes Use cases Goal docs.foldLeft(0)((accum, current) => accum

    + current.length ) Lars Hupel Programming with Type Classes April 22nd, 2013 2 / 27
  4. Patterns Type Classes Use cases Goal docs.foldLeft(0)(_ + _.length) Lars

    Hupel Programming with Type Classes April 22nd, 2013 2 / 27
  5. Patterns Type Classes Use cases Goal (0 /: docs)(_ +

    _.length) Lars Hupel Programming with Type Classes April 22nd, 2013 2 / 27
  6. Patterns Type Classes Use cases Goal docs.map(_.length).sum SELECT SUM(docs.length) FROM

    docs Lars Hupel Programming with Type Classes April 22nd, 2013 2 / 27
  7. Patterns Type Classes Use cases . . “ Good mathematicians

    see analogies. Great mathematicians see analogies between analogies. Stefan Banach . . ” Lars Hupel Programming with Type Classes April 22nd, 2013 3 / 27
  8. Patterns Type Classes Use cases Object-oriented patterns Type Classes Use

    cases Lars Hupel Programming with Type Classes April 22nd, 2013 4 / 27
  9. Patterns Type Classes Use cases Factory Pattern Problem Abstract object

    generation Underlying problem Abstraction over constructors impossible Solution in Java Interface defining abstract factory methods Lars Hupel Programming with Type Classes April 22nd, 2013 5 / 27
  10. Patterns Type Classes Use cases Factory Pattern Problem Abstract object

    generation Underlying problem Abstraction over constructors impossible Solution in Java Interface defining abstract factory methods Lars Hupel Programming with Type Classes April 22nd, 2013 5 / 27
  11. Patterns Type Classes Use cases Factory Pattern Problem Abstract object

    generation Underlying problem Abstraction over constructors impossible Solution in Java Interface defining abstract factory methods Lars Hupel Programming with Type Classes April 22nd, 2013 5 / 27
  12. Patterns Type Classes Use cases Factory Pattern in Scala type

    FictionFactory[T <: Fiction] = (Int, String) => T val sciFi: FictionFactory[SciFi] = new SciFi(true, _, _) Lars Hupel Programming with Type Classes April 22nd, 2013 6 / 27
  13. Patterns Type Classes Use cases Factory Pattern in Scala Problem

    How can factories be organized? Idea Use implicits. But where to put them? Lars Hupel Programming with Type Classes April 22nd, 2013 7 / 27
  14. Patterns Type Classes Use cases Factory Pattern in Scala Problem

    How can factories be organized? Solution Use implicits in companion objects. object SciFi { implicit def factory: FictionFactory[SciFi] = // ... } implicitly[FictionFactory[SciFi]] Lars Hupel Programming with Type Classes April 22nd, 2013 7 / 27
  15. Patterns Type Classes Use cases Excursion: Context Bounds Scala pre-2.8

    def apply[T](implicit ev: Ordering[T]) = // ... Lars Hupel Programming with Type Classes April 22nd, 2013 8 / 27
  16. Patterns Type Classes Use cases Excursion: Context Bounds Scala since

    2.8 def apply[T : Ordering] = // ... Looks nicer, doesn’t it? Lars Hupel Programming with Type Classes April 22nd, 2013 8 / 27
  17. Patterns Type Classes Use cases Factory Pattern in Scala Usage

    Java <T> String doSomething( Factory<T> factory, int nTimes ); Scala def doSomething[T : Factory](nTimes: Int) Lars Hupel Programming with Type Classes April 22nd, 2013 9 / 27
  18. Patterns Type Classes Use cases Factory Pattern in Scala Advantages

    ▶ factory = function ▶ composable ▶ less boilerplate code Lars Hupel Programming with Type Classes April 22nd, 2013 10 / 27
  19. Patterns Type Classes Use cases Recap What have we done

    so far? Lars Hupel Programming with Type Classes April 22nd, 2013 11 / 27
  20. Patterns Type Classes Use cases Adapter Pattern Problem Making third-party

    libraries work together with your code Underlying problem Extending existing classes with additional methods difficult Lars Hupel Programming with Type Classes April 22nd, 2013 12 / 27
  21. Patterns Type Classes Use cases Adapter Pattern Problem Making third-party

    libraries work together with your code Underlying problem Extending existing classes with additional methods difficult Lars Hupel Programming with Type Classes April 22nd, 2013 12 / 27
  22. Patterns Type Classes Use cases Adapter Pattern Problem Making third-party

    libraries work together with your code Underlying problem Extending existing classes with additional methods difficult Solution in Ruby/Python/... Monkey-patching! Lars Hupel Programming with Type Classes April 22nd, 2013 12 / 27
  23. Patterns Type Classes Use cases Adapter Pattern Problem Making third-party

    libraries work together with your code Underlying problem Extending existing classes with additional methods difficult Solution in Java ▶ Composition (Wrapping) ▶ (Inheritance) Lars Hupel Programming with Type Classes April 22nd, 2013 12 / 27
  24. Patterns Type Classes Use cases Type Classes ▶ not to

    be confused with “class” in the Java sense ▶ more of a “family” of types offering common functionality Lars Hupel Programming with Type Classes April 22nd, 2013 13 / 27
  25. Patterns Type Classes Use cases Type Classes . . “

    Polymorphism captures similar structure over different values, while type classes capture similar operations over different structures. Paul Hudak . . ” Lars Hupel Programming with Type Classes April 22nd, 2013 14 / 27
  26. Patterns Type Classes Use cases Example: Numeric trait Numeric[A] {

    def add(a1: A, a2: A): A def neg(a: A): A val zero: A } Looks familiar? It’s a group. Lars Hupel Programming with Type Classes April 22nd, 2013 15 / 27
  27. Patterns Type Classes Use cases Example: Numeric Implementations object FloatNumeric

    extends Numeric[Float] { def add(a1: Float, a2: Float) = a1 + a2 def neg(a: Float) = -a val zero: Float = 0.0f } Lars Hupel Programming with Type Classes April 22nd, 2013 16 / 27
  28. Patterns Type Classes Use cases Example: Numeric Implementations object ComplexNumeric

    extends Numeric[Complex] { def add(a1: Complex, a2: Complex) = new Complex(a1.re + a2.re, a1.im + a2.im) // ... } Lars Hupel Programming with Type Classes April 22nd, 2013 17 / 27
  29. Patterns Type Classes Use cases Example: Numeric Usage def solveEquations[T

    : Numeric]( system: Array[Array[T]] ): Option[Array[T]] = // ... Lars Hupel Programming with Type Classes April 22nd, 2013 18 / 27
  30. Patterns Type Classes Use cases Discussion Advantages ▶ less boilerplate

    code ▶ decoupling ▶ retroactive integration ▶ no “self type” problem Disadvantages ▶ tiny bit of runtime overhead Lars Hupel Programming with Type Classes April 22nd, 2013 19 / 27
  31. Patterns Type Classes Use cases Use case: Algebra We already

    know that one. ▶ semigroups ▶ monoids ▶ groups ▶ semirings ▶ rings ▶ fields ▶ vector spaces ▶ ... Lars Hupel Programming with Type Classes April 22nd, 2013 20 / 27
  32. Patterns Type Classes Use cases Monoids trait Monoid[A] { def

    append(x: A, y: A): A def zero: A } Lars Hupel Programming with Type Classes April 22nd, 2013 21 / 27
  33. Patterns Type Classes Use cases Monoids Implementations Lots of things

    are monoids. ▶ Int, BigInt, ... (obviously) ▶ List[T] ▶ Map[K, V] ▶ Option[T] ▶ ... Lars Hupel Programming with Type Classes April 22nd, 2013 22 / 27
  34. Patterns Type Classes Use cases Monoids Implementations Lots of things

    are monoids. ▶ Int, BigInt, ... (obviously) ▶ List[T] ▶ Map[K, V] ▶ Option[T] ▶ ... Lars Hupel Programming with Type Classes April 22nd, 2013 22 / 27
  35. Patterns Type Classes Use cases Monoids Implementations Lots of things

    are monoids. ▶ Int, BigInt, ... (obviously) ▶ List[T] ▶ Map[K, V] ▶ Option[T] ▶ ... Lars Hupel Programming with Type Classes April 22nd, 2013 22 / 27
  36. Patterns Type Classes Use cases Monoids Implementations Lots of things

    are monoids. ▶ Int, BigInt, ... (obviously) ▶ List[T] ▶ Map[K, V] ▶ Option[T] ▶ ... Lars Hupel Programming with Type Classes April 22nd, 2013 22 / 27
  37. Patterns Type Classes Use cases Monoids Implementations Lots of things

    are monoids. ▶ Int, BigInt, ... (obviously) ▶ List[T] ▶ Map[K, V] ▶ Option[T] ▶ ... Lars Hupel Programming with Type Classes April 22nd, 2013 22 / 27
  38. Patterns Type Classes Use cases Serialization Java serialization: bad Why?

    Reflection, runtime behaviour, ... Lars Hupel Programming with Type Classes April 22nd, 2013 24 / 27
  39. Patterns Type Classes Use cases Serialization Java serialization: bad Why?

    Reflection, runtime behaviour, ... Lars Hupel Programming with Type Classes April 22nd, 2013 24 / 27
  40. Patterns Type Classes Use cases Serialization trait Binary[A] { def

    encode(a: A): Vector[Byte] def decode(bytes: Vector[Byte]): Option[(A, Vector[Byte])] } Lars Hupel Programming with Type Classes April 22nd, 2013 25 / 27