1. Обзор
В этом руководстве мы расскажем, как создать пользовательское исключение в Java.
Мы покажем, как пользовательские исключения реализованы и используются как для проверенных, так и для непроверенных исключений.
2. Необходимость в пользовательских исключениях
Исключения Java охватывают почти все общие исключения, которые неизбежно случаются в программировании.
Однако нам иногда нужно дополнять эти стандартные исключения своими собственными.
Вот основные причины введения пользовательских исключений:
- Исключения бизнес-логики — исключения, относящиеся к бизнес-логике и рабочему процессу. Они помогают пользователям приложения или разработчикам понять, в чем именно заключается проблема.
- Для перехвата и специальной обработки подмножества существующих исключений Java.
Исключения Java можно проверять и снимать. В следующих разделах мы рассмотрим оба этих случая.
3. Пользовательское проверенное исключение
Проверенные исключения — это исключения, которые необходимо обрабатывать явно.
Рассмотрим фрагмент кода, который возвращает первую строку файла:
try (Scanner file = new Scanner(new File(fileName))) {
if (file.hasNextLine()) return file.nextLine();
} catch(FileNotFoundException e) {
// Logging, etc
}
Приведенный выше код представляет собой классический способ обработки проверенных исключений Java. Хотя код выдает FileNotFoundException
, неясна точная причина — файл не существует или имя файла недопустимо.
Чтобы создать пользовательское исключение, мы должны расширить класс java.lang.Exception .
Давайте посмотрим на пример этого, создав пользовательское проверенное исключение с именем IncorrectFileNameException
:
public class IncorrectFileNameException extends Exception {
public IncorrectFileNameException(String errorMessage) {
super(errorMessage);
}
}
Обратите внимание, что мы также должны предоставить конструктор, который принимает String
в качестве сообщения об ошибке и вызывает конструктор родительского класса.
Это все, что нам нужно сделать, чтобы определить пользовательское исключение.
Далее давайте посмотрим, как мы можем использовать пользовательское исключение в нашем примере:
try (Scanner file = new Scanner(new File(fileName))) {
if (file.hasNextLine())
return file.nextLine();
} catch (FileNotFoundException e) {
if (!isCorrectFileName(fileName)) {
throw new IncorrectFileNameException("Incorrect filename : " + fileName );
}
//...
}
Мы создали и использовали специальное исключение, поэтому теперь пользователь может точно знать, что это за исключение.
Этого достаточно? Следовательно, мы теряем основную причину исключения.
Чтобы исправить это, мы также можем добавить в конструктор параметр java.lang.Throwable .
Таким образом, мы можем передать корневое исключение вызову метода:
public IncorrectFileNameException(String errorMessage, Throwable err) {
super(errorMessage, err);
}
Теперь IncorrectFileNameException
используется вместе с основной причиной исключения:
try (Scanner file = new Scanner(new File(fileName))) {
if (file.hasNextLine()) {
return file.nextLine();
}
} catch (FileNotFoundException err) {
if (!isCorrectFileName(fileName)) {
throw new IncorrectFileNameException(
"Incorrect filename : " + fileName , err);
}
// ...
}
Вот как мы можем использовать пользовательские исключения , не теряя основной причины, из-за которой они произошли.
4. Пользовательское непроверенное исключение
В нашем же примере предположим, что нам нужно пользовательское исключение, если имя файла не содержит никакого расширения.
В этом случае нам понадобится пользовательское непроверенное исключение, подобное предыдущему, так как эта ошибка будет обнаружена только во время выполнения.
Чтобы создать пользовательское непроверенное исключение, нам нужно расширить класс java.lang.RuntimeException
:
public class IncorrectFileExtensionException
extends RuntimeException {
public IncorrectFileExtensionException(String errorMessage, Throwable err) {
super(errorMessage, err);
}
}
Таким образом, мы можем использовать это пользовательское непроверенное исключение в нашем примере:
try (Scanner file = new Scanner(new File(fileName))) {
if (file.hasNextLine()) {
return file.nextLine();
} else {
throw new IllegalArgumentException("Non readable file");
}
} catch (FileNotFoundException err) {
if (!isCorrectFileName(fileName)) {
throw new IncorrectFileNameException(
"Incorrect filename : " + fileName , err);
}
//...
} catch(IllegalArgumentException err) {
if(!containsExtension(fileName)) {
throw new IncorrectFileExtensionException(
"Filename does not contain extension : " + fileName, err);
}
//...
}
5. Вывод
Пользовательские исключения очень полезны, когда нам нужно обрабатывать определенные исключения, связанные с бизнес-логикой. При правильном использовании они могут служить практическим инструментом для лучшей обработки исключений и регистрации.
Код примеров, использованных в этой статье, доступен на GitHub .