#java #exception-handling
#java #исключение
Вопрос:
У меня есть следующий код. В этом fn2
фактически генерируется исключение, и оно перехватывается в самой функции. В функции fn1
компилятор жалуется на необработанное исключение, поскольку fn2
объявлено, что оно генерирует исключение.
Почему это так? Поскольку исключение перехватывается внутри fn2
, оно не должно жаловаться, верно?
Пожалуйста, объясните поведение.
public class ExepTest {
/**
* @param args
*/
public static void main(String[] args) {
ExepTest exT = new ExepTest();
exT.fn1();
}
public void fn1(){
fn2();//compilation error
}
public void fn2() throws Exception{
try{
throw new Exception();
}
catch(Exception ex){
System.out.println("Exception caught");
}
}
}
Ответ №1:
Компилятор не знает / не может знать, что во время выполнения никакое исключение не будет выдано fn2()
, поскольку объявлено, что оно может выдавать исключение, вот почему вы получили ошибку.
Комментарии:
1. Другими словами: если вы скажете ему , что a использует методы
throws Exception
, то компилятор поверит вам . Он не будет проверять, так ли это на самом деле (в некоторых случаях он даже не может проверить).2. @Joachim: Это отношения, основанные на взаимном доверии.
Ответ №2:
Удалите подпись throws Exception
из fn2()
Ответ №3:
Сигнатура метода fn2 — это все, что здесь имеет значение. В этой подписи вы заявляете, что fn2 может выдавать исключение. Любой код, вызывающий метод, который может вызвать исключение, должен обрабатывать исключение eexception.
Ответ №4:
public void fn2() throws Exception
. Компилятор видит это объявление и ожидает, что каждый вызывающий объект fn2
будет обрабатывать / повторно генерировать исключение.
Ответ №5:
Исключение генерируется fn2
, а не внутри него. Таким образом, он будет фактически выдан там, где он вызывается. Поскольку он вызывается в fn1
, он ведет себя следующим образом.
Ответ №6:
Вам нужно поместить вызов на fn2()
в блок try-catch или объявить, что fn1
также генерирует исключение.
Ответ №7:
public void fn1(){
fn2();//compilation error
}
public void fn2() throws Exception{
try{
throw new Exception();
}
catch(Exception ex){
System.out.println("Exception caught");
}
}
}
Здесь компилятор не распознает, обработали вы исключение или нет. Это просто предполагает, что fn2 выдает исключение, как вы объявили, и именно поэтому оно показывает ошибку.
Чтобы запустить программу, либо удалите throws Exception
из fn2, напишите throws Exception
в fn1, либо обработайте ее в try..catch
в fn1.