Ausnahmen geprüft und nicht
Kurz gesagt, es sind Ausnahmen erforderlich, um das positive Szenario (wenn alles gut läuft) vom negativen Szenario zu trennen (wenn ein Fehler auftritt und das positive Szenario unterbrochen wird). Dies ist nützlich, da der Code sehr oft nur wenige Informationen enthält, um den Fehler zu beheben, und Sie Informationen über die oben genannten Ereignisse übermitteln müssen.
Zum Beispiel gibt es eine Funktion zum Lesen einer Nummer aus einer Datei (oder keine Nummer, es spielt keine Rolle):
String readStoredData(String id) throws FileNotFoundException, IOException {
File file = new File(storage, id + ".dat");
try (BufferedReader in = new BufferedReader(new FileReader(file))) {
return in.readLine();
}
}
Wie Sie sehen, gibt es hier keinen Code, der entscheidet, was im Fehlerfall zu tun ist. Und es ist nicht klar, was zu tun ist - das Programm beenden, "", null oder etwas anderes zurückgeben? Daher werden Ausnahmen in deklariert throws
und irgendwo auf dem Anrufer behandelt:
int initCounter(String name) throws IOException, NumberFormatException {
try {
return Integer.parseInt(readStoredData(name));
} catch (FileNotFoundException e) {
return 0;
}
}
Ausnahmen in Java sind in aktiviert und deaktiviert unterteilt. In diesem Fall wird IOException
es aktiviert - Sie müssen es deklarieren throws
und dann irgendwo verarbeiten, der Compiler überprüft es. NumberFormatException
nicht überprüfbar - seine Verarbeitung bleibt auf dem Gewissen des Programmierers und der Compiler wird Sie nicht kontrollieren.
Es gibt auch eine dritte Art von Ausnahme - schwerwiegende Fehler ( Error
), deren Behandlung normalerweise nicht sinnvoll ist. Sie sollten sich also keine Sorgen machen.
, – , .
:
;
( – ) .
- , . .
Scala?
Scala: ( ), .
Try[T]
– , , . Scala:
def readStoredData(id: String): Try[String] =
Try {
val file = new File(storage, s"$id.dat")
val source = Source.fromFile(file)
try source.getLines().next()
finally source.close()
}
def initCounter(name: String): Try[Int] = {
readStoredData(name)
.map(_.toInt)
.recover {
case _: FileNotFoundException => 0
}
}
, , readStoredData
String
, Try[String]
– . Try Java – , .
:
(
Either[Error, T]
, );
happy-path , (
Try/get
for/map/flatMap
);
Java - , ( Java , ).
( Try[String]
– ). Option[T]
– , Future[T]
– ..
, – . / Java, ( ).
:
FileNotFoundException
,
IOException
–
:
def readStoredData(id: String): Option[Try[String]] = {
val file = new File(storage, s"$id.dat")
if (file.exists()) Some(
Try {
val source = Source.fromFile(file)
try source.getLines().next()
finally source.close()
}
)
else None
}
Option[Try[String]]
, , :
None
–
Some(Success(string))
–
Some(Failure(exception))
– ,
Try
. Java , null. .
Die Fülle an Typen erzeugt mehr visuelles Rauschen und erfordert häufig komplexeren Code, wenn mit mehreren Effekten gleichzeitig gearbeitet wird. Im Gegenzug bietet es selbstdokumentierenden Code und ermöglicht es dem Compiler, viele Fehler zu finden.