Type Classes in Scala

756 views

Published on

Präsentation bei der Scala User Group über Type Classes in Scala.

Published in: Technology
0 Comments
0 Likes
Statistics
Notes
  • Be the first to comment

  • Be the first to like this

No Downloads
Views
Total views
756
On SlideShare
0
From Embeds
0
Number of Embeds
8
Actions
Shares
0
Downloads
4
Comments
0
Likes
0
Embeds 0
No embeds

No notes for slide
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • Type Classes in Scala

    1. 1. TYPE CLASSESAd-Hoc Polymorphismus ohne Unterklassen Scala User Group Köln/Bonn @scalacgn 1
    2. 2. POLYMORPHISMUS 2
    3. 3. POLYMORPHISMUS• Parametrisiert • Generische Funktionen und Datentypen 2
    4. 4. POLYMORPHISMUS• Parametrisiert • Generische Funktionen und Datentypen• Ad-hoc • Methoden- und Operator-Overloading • Unterklassen (Subtype Polymorphismus) • Type Classes 2
    5. 5. CASE CLASSES SERIALISIEREN package model {   case class Person(firstName: String, lastName: String)   case class Restaurant(name: String, address: String) } 3
    6. 6. CASE CLASSES SERIALISIEREN package model {   case class Person(firstName: String, lastName: String)   case class Restaurant(name: String, address: String) } Neue JSON CSV XML Funktion Person toJson toCsv toXml Restaurant toJson toCsv toXml Neuer Typ 3
    7. 7. ÜBERLADEN1. object JsonSerializer {2.   def toJson(person: Person): String = """{ name : "%s %s" }""".format(person.firstName, person.lastName)3.   def toJson(r: Restaurant) = """{ name : "%s"; address: "%s" }""".format(r.name, r.address)4. }5.  6. object CsvSerializer {7.   def toCSV(person: Person): String = "%s,%s".format(person.firstName, person.lastName)8.   def toCSV(r: Restaurant): String = "%s,%s".format(r.name, r.address)9. } 4
    8. 8. ÜBERLADEN1. object JsonSerializer {2.   def toJson(person: Person): String = """{ name : "%s %s" }""".format(person.firstName, person.lastName)3.   def toJson(r: Restaurant) = """{ name : "%s"; address: "%s" }""".format(r.name, r.address)4. }5.  6. object CsvSerializer {7.   def toCSV(person: Person): String = "%s,%s".format(person.firstName, person.lastName)8.   def toCSV(r: Restaurant): String = "%s,%s".format(r.name, r.address)9. } +Einfach - Kein Zusammenhang außer Methodenname 4
    9. 9. UNTERKLASSEN1. abstract class Serializer {2.   def toJson: String3.   def toCSV: String4. }5.  6. case class Person(firstName: String, lastName: String) extends Serializer {7.   override def toJson: String = """{ name : "%s %s" }""".format(firstName, lastName)8.   override def toCSV: String = "%s,%s".format(firstName, lastName)9. }10.  11. case class Restaurant(name: String, address: String) extends Serializer {12.   override def toJson(r: Restaurant) = """{ name : "%s"; address: "%s" }""".format(r.name, r.address)13.   override def toCSV(r: Restaurant): String = "%s,%s".format(r.name, r.address)14. }1. import models._2. Person("Max", "Mustermann").toJson 5
    10. 10. UNTERKLASSEN1. abstract class Serializer {2.   def toJson: String3.   def toCSV: String4. }5.  6. case class Person(firstName: String, lastName: String) extends Serializer {7.   override def toJson: String = """{ name : "%s %s" }""".format(firstName, lastName)8.   override def toCSV: String = "%s,%s".format(firstName, lastName)9. }10.  11. case class Restaurant(name: String, address: String) extends Serializer {12.   override def toJson(r: Restaurant) = """{ name : "%s"; address: "%s" }""".format(r.name, r.address)13.   override def toCSV(r: Restaurant): String = "%s,%s".format(r.name, r.address)14. }1. import models._2. Person("Max", "Mustermann").toJson+ Einfach neue Klassen hinzuzufügen- Modellklassen müssen von Serializer ableiten 5
    11. 11. TRAITS1. trait JsonSerializer {2.   def toJson: String3. }4.  5. trait CsvSerializer {6.   def toCSV: String7. }8.  9. case class Person(firstName: String, lastName: String) extends JsonSerializer with CsvSerializer {10.   override def toJson: String = """{ name : "%s %s" }""".format(firstName, lastName)11.   override def toCSV: String = "%s,%s".format(firstName, lastName)12. }13.  14. case class Restaurant(name: String, address: String)  extends JsonSerializer with CsvSerializer {15.   override def toJson(r: Restaurant) = """{ name : "%s"; address: "%s" }""".format(r.name, r.address)16.   override def toCSV(r: Restaurant): String = "%s,%s".format(r.name, r.address)17. } 6
    12. 12. TRAITS1. trait JsonSerializer {2.   def toJson: String3. }4.  5. trait CsvSerializer {6.   def toCSV: String7. }8.  9. case class Person(firstName: String, lastName: String) extends JsonSerializer with CsvSerializer {10.   override def toJson: String = """{ name : "%s %s" }""".format(firstName, lastName)11.   override def toCSV: String = "%s,%s".format(firstName, lastName)12. }13.  14. case class Restaurant(name: String, address: String)  extends JsonSerializer with CsvSerializer {15.   override def toJson(r: Restaurant) = """{ name : "%s"; address: "%s" }""".format(r.name, r.address)16.   override def toCSV(r: Restaurant): String = "%s,%s".format(r.name, r.address)17. }- Serialisieren hat nichts mit der Logik zu tun, Code steht nicht immer zur Verfügung 6
    13. 13. TYPE CASING1. object JsonSerializer {2.   def toJson(x: AnyRef): String = x match {3.     case person: Person => """{ name : "%s %s" }""".format(person.firstName, person.lastName)4.     case r: Restaurant => """{ name : "%s"; address: "%s" }""".format(r.name, r.address)5.   }6.  7. object CsvSerializer {8.   def toCSV(x: AnyRef): String = x match {9.     case person: Person => "%s,%s".format(person.firstName, person.lastName)10.     case r: Restaurant => "%s,%s".format(r.name, r.address)11.   }12. } 7
    14. 14. TYPE CASING1. object JsonSerializer {2.   def toJson(x: AnyRef): String = x match {3.     case person: Person => """{ name : "%s %s" }""".format(person.firstName, person.lastName)4.     case r: Restaurant => """{ name : "%s"; address: "%s" }""".format(r.name, r.address)5.   }6.  7. object CsvSerializer {8.   def toCSV(x: AnyRef): String = x match {9.     case person: Person => "%s,%s".format(person.firstName, person.lastName)10.     case r: Restaurant => "%s,%s".format(r.name, r.address)11.   }12. }+ Einfach neue Funktionen hinzuzufügen- Viele Eingriffe bei neuem Typ 7
    15. 15. TYPE CLASSES (1)1. package serializer2.  3. trait CsvSerializable[T] {4.   def toCsv(t: T): String5. }6.  7. object CsvSerializable {8.   import models._9.  10.   def toCsv[T](t: T)(implicit serializer: CsvSerializable[T]): String =11.     serializer.toCsv(t)12.  13.   implicit object UserSerializable extends CsvSerializable[Person] {14.     def toCsv(person: User) String =15.       "%s,%s".format(person.firstName, person.lastName)16.   }17. }1. import serializer._2. val user = User(name = "Max Musterbro")3. val csvHelper = implicitly[CsvSerializable[User]]4. csvHelper.toCsv(user)5.  6. // Oder7. import serializer.CsvSerializable._8. toCsv(User(name = "Max Musterbro")) 8
    16. 16. TYPE CLASSES (2)1. trait JsonSerializable[T] {2.   def toJson(t: T): String3. }4.  5. object JsonSerializable {6.   import models._7.  8.   implicit object UserSerializable extends JsonSerializable[Person] {9.     def toJson(person: Person): String =10. """{ name : "%s", status: "%s" }""".format(person.firstName, person.lastName)11.   }12.  13.   class UserSerializer(p: Person) {14.     def toJson: String = UserSerializable.toJson(p)15.   }16.  17.   implicit def UserToSerializer(p: Person) = new UserSerializer(p) 1. import serializer.JsonSerializable._ 2. User(name = "Max Musterbro").toJson 9
    17. 17. TYPE CLASSES (3) 10
    18. 18. TYPE CLASSES (3)• Definition 10
    19. 19. TYPE CLASSES (3)• Definition • Trait mit Parameter 10
    20. 20. TYPE CLASSES (3)• Definition • Trait mit Parameter • Companion Object mit Default Implementationen 10
    21. 21. TYPE CLASSES (3)• Definition • Trait mit Parameter • Companion Object mit Default Implementationen• Beispiele in Scala: scala.math.Ordering und scala.math.Numeric 10
    22. 22. TYPE CLASSES (3)• Definition • Trait mit Parameter • Companion Object mit Default Implementationen• Beispiele in Scala: scala.math.Ordering und scala.math.Numeric•+ Gut erweiterbar 10
    23. 23. TYPE CLASSES (3)• Definition • Trait mit Parameter • Companion Object mit Default Implementationen• Beispiele in Scala: scala.math.Ordering und scala.math.Numeric•+ Gut erweiterbar• - Viel Code, implicits manchmal undurchsichtig 10
    24. 24. > CODE• https://twitter.com/scalacgn• http://xing.to/scala 11

    ×