Ich habe in Google nach den Unterschieden zwischen a case class
und a gesucht class
. Jeder erwähnt, dass Sie die Fallklasse verwenden, wenn Sie einen Mustervergleich für die Klasse durchführen möchten. Verwenden Sie andernfalls Klassen und erwähnen Sie einige zusätzliche Vorteile wie Gleichheit und Überschreiben von Hash-Code. Aber sind dies die einzigen Gründe, warum man eine Fallklasse anstelle einer Klasse verwenden sollte?
Ich denke, es sollte einen sehr wichtigen Grund für diese Funktion in Scala geben. Was ist die Erklärung oder gibt es eine Ressource, um mehr über die Scala-Fallklassen zu erfahren?
quelle
Technisch gesehen gibt es keinen Unterschied zwischen einer Klasse und einer Fallklasse - selbst wenn der Compiler bei der Verwendung von Fallklassen einige Dinge optimiert. Eine Fallklasse wird jedoch verwendet, um die Kesselplatte für ein bestimmtes Muster zu beseitigen, das algebraische Datentypen implementiert .
Ein sehr einfaches Beispiel für solche Typen sind Bäume. Ein Binärbaum kann beispielsweise folgendermaßen implementiert werden:
Damit können wir Folgendes tun:
Beachten Sie, dass Bäume mit derselben Syntax konstruieren und dekonstruieren (durch Musterübereinstimmung). Dies ist auch genau die Art und Weise, wie sie gedruckt werden (minus Leerzeichen).
Sie können auch mit Hash-Maps oder -Sätzen verwendet werden, da sie einen gültigen, stabilen Hash-Code haben.
quelle
(Sie haben bereits alle bis auf den letzten erwähnt).
Dies sind die einzigen Unterschiede zu regulären Klassen.
quelle
Niemand erwähnte, dass Fallklassen auch Instanzen
Product
dieser Methoden sind und diese daher erben:Dabei
productArity
gibt der die Anzahl der Klassenparameter zurück,productElement(i)
gibt den i- ten Parameter zurück undproductIterator
ermöglicht das Durchlaufen dieser Parameter .quelle
Niemand erwähnte, dass Fallklassen
val
Konstruktorparameter haben, dies ist jedoch auch die Standardeinstellung für reguläre Klassen (was meiner Meinung nach eine Inkonsistenz im Design von Scala darstellt). Dario implizierte dies, wo er feststellte, dass sie " unveränderlich " sind.Beachten Sie, dass Sie die Standardeinstellung überschreiben können, indem Sie jedem Konstruktorargument
var
for case-Klassen voranstellen . Wenn Fallklassen jedoch veränderlich gemacht werden, sind ihreequals
undhashCode
Methoden zeitlich variabel. [1]sepp2k bereits erwähnt , dass Fallklassen automatisch erzeugen
equals
undhashCode
Methoden.Außerdem erwähnte niemand, dass Fallklassen automatisch einen Begleiter
object
mit demselben Namen wie die Klasse erstellen , dieapply
undunapply
Methoden enthält . Dieapply
Methode ermöglicht das Erstellen von Instanzen ohne Voranstellen mitnew
. Dieunapply
Extraktionsmethode ermöglicht den Mustervergleich, den andere erwähnt haben.Auch der Compiler optimiert die Geschwindigkeit
match
-case
Mustervergleich für Fallklassen [2].[1] Fallklassen sind cool
[2] Fallklassen und Extraktoren, S. 15 .
quelle
Das Fallklassenkonstrukt in Scala kann auch als Annehmlichkeit zum Entfernen von Boilerplate angesehen werden.
Beim Erstellen einer Fallklasse bietet Scala Folgendes.
apply
Methode, die Sie als Factory-Methode verwenden können. Sie erhalten den syntaktischen Zuckervorteil, dass Sie das neue Schlüsselwort nicht verwenden müssen.Da die Klasse unveränderlich ist, erhalten Sie Accessoren, die nur die Variablen (oder Eigenschaften) der Klasse sind, aber keine Mutatoren (also keine Möglichkeit, die Variablen zu ändern). Die Konstruktorparameter stehen Ihnen automatisch als öffentliche schreibgeschützte Felder zur Verfügung. Viel schöner zu verwenden als Java Bean Konstrukt.
hashCode
,equals
undtoString
Methoden standardmäßig aktiviert und dasequals
Verfahren vergleicht ein strukturell - Objekt. Einecopy
Methode wird generiert, um ein Objekt klonen zu können (wobei einige Felder neue Werte für die Methode bereitstellen).Der größte Vorteil, wie bereits erwähnt, ist die Tatsache, dass Sie Musterübereinstimmungen für Fallklassen durchführen können. Der Grund dafür ist, dass Sie die
unapply
Methode erhalten, mit der Sie eine Fallklasse dekonstruieren können, um ihre Felder zu extrahieren.Im Wesentlichen erhalten Sie von Scala beim Erstellen einer Fallklasse (oder eines Fallobjekts, wenn Ihre Klasse keine Argumente akzeptiert) ein Singleton-Objekt, das als Factory und als Extraktor dient .
quelle
copy
Methode die Felder ändern kann:val x = y.copy(foo="newValue")
Abgesehen von dem, was die Leute bereits gesagt haben, gibt es einige grundlegendere Unterschiede zwischen
class
undcase class
1.
Case Class
muss nicht explizit seinnew
, während class mit aufgerufen werden mussnew
2.By Standardkonstruktorparameter sind privat in
class
, während seine öffentlich incase class
3.
case class
Vergleichen Sie sich nach Wertquelle
Laut Scalas Dokumentation :
Ein weiteres Merkmal des Schlüsselworts case ist, dass der Compiler automatisch mehrere Methoden für uns generiert, einschließlich der bekannten Methoden toString, equals und hashCode in Java.
quelle
Klasse:
Wenn wir jedoch denselben Code verwenden, aber die Fallklasse verwenden:
Personenklasse:
Mustervergleich:
Objekt: Singleton:
quelle
Um das ultimative Verständnis für eine Fallklasse zu haben:
Nehmen wir die folgende Definition der Fallklasse an:
und machen Sie dann im Terminal Folgendes:
Scala 2.12.8 gibt Folgendes aus:
Wie wir sehen können, erzeugt der Scala-Compiler eine reguläre Klasse
Foo
und ein BegleitobjektFoo
.Lassen Sie uns die kompilierte Klasse durchgehen und kommentieren, was wir haben:
Foo
Klasse, unveränderlich:scala.Product
:scala.Equals
Merkmals, um Fallklasseninstanzen für Gleichheit vergleichbar zu machen, indem==
:java.lang.Object.hashCode
für die Einhaltung des Equals-Hashcode-Vertrags:java.lang.Object.toString
:new
Schlüsselwort:Objekt Foo: - Methode
apply
zur Instanziierung ohnenew
Schlüsselwort:unupply
zur Verwendung der Fallklasse Foo beim Mustervergleich:scala.runtime.AbstractFunction2
für einen solchen Trick:tupled
from object gibt eine Funktion zurück, um ein neues Foo zu erstellen, indem ein Tupel aus 2 Elementen angewendet wird.Die Fallklasse ist also nur syntaktischer Zucker.
quelle
Im Gegensatz zu Klassen werden Fallklassen nur zum Speichern von Daten verwendet.
Fallklassen sind für datenzentrierte Anwendungen flexibel. Dies bedeutet, dass Sie Datenfelder in Fallklassen definieren und Geschäftslogik in einem Begleitobjekt definieren können. Auf diese Weise trennen Sie die Daten von der Geschäftslogik.
Mit der Kopiermethode können Sie einige oder alle erforderlichen Eigenschaften von der Quelle erben und nach Belieben ändern.
quelle
Niemand erwähnte, dass das Begleitobjekt der
tupled
Fallklasse eine Verteidigung hat, die einen Typ hat:Der einzige Anwendungsfall, den ich finden kann, ist, wenn Sie eine Fallklasse aus einem Tupel erstellen müssen. Beispiel:
Sie können dasselbe ohne Tupel tun, indem Sie ein Objekt direkt erstellen. Wenn Ihre Datensätze jedoch als Liste von Tupeln mit Arität 20 (Tupel mit 20 Elementen) ausgedrückt werden, können Sie Tupel verwenden.
quelle
Eine Fallklasse ist eine Klasse, die mit der
match/case
Anweisung verwendet werden kann.Siehst du das
case
eine Instanz der Klasse Fun folgt, deren zweiter Parameter ein Var ist. Dies ist eine sehr schöne und leistungsstarke Syntax, die jedoch nicht mit Instanzen einer Klasse funktioniert. Daher gibt es einige Einschränkungen für Fallklassen. Und wenn diese Einschränkungen eingehalten werden, ist es möglich, automatisch Hashcode und Gleichheit zu definieren.Der vage Ausdruck "ein rekursiver Zerlegungsmechanismus über Mustervergleich" bedeutet nur "es funktioniert mit
case
". (In der Tat wird die folgende Instanz mit der folgenden Instanzmatch
verglichen (verglichen mit dieser).case
Scala muss beide zerlegen und rekursiv zerlegen, woraus sie bestehen.)Für welche Fallklassen sind nützlich? Der Wikipedia-Artikel über algebraische Datentypen enthält zwei gute klassische Beispiele: Listen und Bäume. Die Unterstützung algebraischer Datentypen (einschließlich des Vergleichs) ist ein Muss für jede moderne Funktionssprache.
Für welche Fallklassen sind sie nicht nützlich? Einige Objekte haben Status, der Code
connection.setConnectTimeout(connectTimeout)
ist nicht für Fallklassen.Und jetzt können Sie A Tour of Scala: Fallklassen lesen
quelle
Ich denke, insgesamt haben alle Antworten eine semantische Erklärung zu Klassen und Fallklassen gegeben. Dies könnte sehr relevant sein, aber jeder Neuling in Scala sollte wissen, was passiert, wenn Sie eine Fallklasse erstellen. Ich habe geschrieben das Antwort geschrieben, die die Fallklasse auf den Punkt bringt.
Jeder Programmierer sollte wissen, dass er, wenn er vorgefertigte Funktionen verwendet, einen vergleichsweise weniger Code schreibt, was es ihm ermöglicht, den optimiertesten Code zu schreiben, aber die Leistung bringt große Verantwortung mit sich. Verwenden Sie daher vorgefertigte Funktionen mit sehr Vorsicht.
Einige Entwickler vermeiden das Schreiben von Fallklassen aufgrund zusätzlicher 20 Methoden, die Sie durch Zerlegen der Klassendatei sehen können.
Bitte beziehen Sie sich auf diesen Link, wenn Sie alle Methoden innerhalb einer Fallklasse überprüfen möchten .
quelle
quelle
Einige der wichtigsten Funktionen von
case classes
sind unten aufgeführtnew
Schlüsselwort .Beispiel für einen Scala-Code auf einer Scala-Geige aus den Scala-Dokumenten.
https://scalafiddle.io/sf/34XEQyE/0
quelle