2016-07-29 45 views
0

Ich lerne Play2 Framework und benutze implizite Funktionen. Ich bin etwas Position Objekt zu Json Umwandlung:Scala: Definiere implizite Funktionen in einem Objekt oder in einer Klasse

implicit val locationWrites = new Writes[Position] { 
    def writes(position: Position) = Json.obj(
     "lat" -> position.lat, 
     "lon" -> position.lon 
    ) 
} 

Sollte ich:

object JsonConversion { 
    implicit val locationWrites = new Writes[Position] { 
    def writes(position: Position) = Json.obj(
     "lat" -> position.lat, 
     "lon" -> position.lon 
    ) 
    } 
} 

oder soll ich tun:

class JsonConversion { 
    implicit val locationWrites = new Writes[Position] { 
    def writes(position: Position) = Json.obj(
     "lat" -> position.lat, 
     "lon" -> position.lon 
    ) 
    } 
} 

und importieren diese class oder object wo diese implizite Funktionen wird verwendet.

Was ist der grundlegende Unterschied in Bezug auf Instanzen und Skalierbarkeit solcher impliziten Funktionen, zum Beispiel wenn sie gleichzeitig aufgerufen werden sollen?

+0

Wie werden Sie "eine Klasse importieren"? Versuchen Sie es ... – Dima

Antwort

1

Weder wirklich. Es gibt einen viel saubereren Weg, um all Ihre Domain zusammen zu halten und etwas, das die Leute normalerweise vergessen werden. Sie können

im Begleitobjekt setzen implict

Hier ist, wo Sie wirklich setzen sollen:

class Position { ... } 
object Position { 
    implicit val positionWrites = new Writes[Position] { 
    def writes(position: Position) = Json.obj(
    "lat" -> position.lat, 
    "lon" -> position.lon 
    ) 
    } 
} 

Standardmäßig wird implizit Auflösung des Begleit-Objekt suchen. Dies verhindert, dass die Domain verstreut wird und es keine merkwürdigen Dateien voller JSON-Formate gibt. Sie können Dinge an den richtigen Stellen gekoppelt halten und es ist einfach zu wissen, wo sich Dinge ändern müssen, wenn Sie Ihre Klassen aktualisieren.

Nebenbei bemerkt, Play hat fortgeschrittenere JSON-Format-Generation mit einigen lustigen Makros. Sie können Json.format[Type] oder Json.writes[Type] oder nur Json.reads[Type] verwenden, um einfach das Format zu erstellen, das Sie ohne manuellen Aufwand benötigen.

implicit val positionFormat = Json.format[Position] 
+0

Kopplung von Domänenmodellen mit JSON-Stäbe ist eines der Dinge, die Sie davon vermeiden sollten. Formatierer werden hauptsächlich in API/Service/Web-Modulen verwendet. Allerdings stammt das Domänenmodell selbst aus einem Geschäftsproblem und hat nichts damit zu tun, wie Sie es dem Client darstellen möchten. Ich bin sicher, niemand möchte die Domain-Modelle ändern, um neue Formatierer zum Beispiel für ProtoBuf, Avro, XML, ... hinzuzufügen –

+0

Hallo @SorooshSarabadani Du hast eine einfache Play-App für jemanden, der gerade angefangen hat. Die meisten Menschen haben kilometrische Merkmale, die sie in alles einmischen, das ist ein Weg, aber für das einfache Szenario, warum vermeidest du es? – flavian

+0

Hallo Flavian, ich erkläre gerade, warum erfahrene Entwickler dazu neigen, solche einfachen Dinge zu vergessen;) –

0

setzen Sie Ihre implizite Methode in einem Objekt und es auf diese Weise importieren:

import JsonConversion._ 

Aus Performance-Sicht Sie keine Bedenken haben sollten, da viele Anrufe ohne Nebenwirkung ausgeführt werden können.

+0

Tank Sie Soroosh Sarabadani, dachte ich darüber nach, eine Instanz (eine instanziierte Klasse: objectif, aber nicht Singleton) im Rahmen jeder Funktion zu haben, die Position in Json umwandelt? Die Tatsache, dass es keine Nebenwirkung gibt, bedeutet, dass die Funktion von einem Singleton gleichzeitig aufgerufen werden kann? – Antonin

+0

Sie müssen das nicht wirklich tun und brauchen sich keine Gedanken über die Skalierbarkeit zu machen. Da Ihre Klasse keinen Status hat, führt das mehrfache Instanziieren zu keinem Ergebnis für Sie. Referentielle Transparenz ist ein guter Grund, eine Methode ohne Probleme gleichzeitig aufzurufen. Bilions gleichzeitiger Aufrufe dieser Art von Funktionen können ausgeführt werden, ohne irgendwelche Engpässe oder Probleme zu verursachen. –

+0

Danke Soroosh! – Antonin