Проверяются ли множественные исключения или время выполнения? - PullRequest
3 голосов
/ 06 мая 2010

У меня есть цепочка исключений, в которой method1 выбрасывает исключение в method2, а исключение в main. По какой-то причине компилятор заставляет меня иметь дело с ошибкой в ​​method2 и помечает ее как ошибку, если я не делаю, указывая, что это проверенное исключение. Но когда тот же Exception отбрасывается дальше по строке до main, компилятор позволяет мне его игнорировать и не отображает никаких ошибок.

Исходное исключение в method1 - это ParseException, которое проверено. Но у метода есть общее предложение throws Exception в заголовке, и тот же объект брошен в method2, который имеет идентичное предложение throws Exception. Когда и как это исключение теряет статус проверки / перехвата компилятором?

Отредактировано, чтобы уточнить:

public void method1() throws Exception{
   // code that may generate ParseException
}

public void method2() throws Exception{
   method1(); //compiler error (if the throws clause is left out)
}

public static void main(String[] args){
   method2(); //ignored by compiler, even though the exception isn't caught or thrown or handled at all
}

Edit: Извините всех, вопрос был основан на ошибке ... В основном методе было предложение throws Exception, которое я пропустил. Я удалил это, и код теперь ведет себя как ожидалось. Спасибо за помощь!

Ответы [ 4 ]

6 голосов
/ 06 мая 2010

Независимо от того, проверено ли исключение или нет, оно полностью зависит от того, какое это исключение: если оно является RuntimeException или его подклассом, оно не проверяется; в противном случае это так. (И да, RuntimeException - это подкласс Exception - одна из ошибок проектирования библиотеки Java, но не самая главная.)

То, что проверяет компилятор, это сигнатуры методов. Таким образом, выбрасываемое исключение не имеет значения (для этой цели). Если методы говорят throws Exception, то вы должны перехватить Exception в своем методе или объявить, что метод throws Exception. Методы всегда должны использовать максимально узкое throws предложение & mdash; например, не throws Exception, а throws ParseException.

(я говорю «не имеет значения (для этой цели)», потому что, конечно, одна из других вещей, которые будет делать компилятор, это проверка того, что вы не выбрасываете проверенные исключения, которые не покрываются ваше throws предложение.)

Редактировать Код, добавленный в редакторе, не будет компилироваться: 1. Он вызывает метод экземпляра без экземпляра, и 2. main необходимо объявить, что он выдает Exception.

Этот код решает другие проблемы и (правильно) демонстрирует, что main нуждается в предложении throws Exception:

public class CheckTest
{
    public static final void main(String[] params)
    {
        new CheckTest().method2();
    }

    public void method1() throws Exception{
        throw new java.text.ParseException("foo", 2);
    }

    public void method2() throws Exception{
        this.method1();
    }
}

Результат:

CheckTest.java:27: unreported exception java.lang.Exception; must be caught or declared to be thrown

                new CheckTest().method2();
                                       ^
1 error
3 голосов
/ 06 мая 2010

Проверенное исключение не перестает быть проверенным исключением. Способ, которым вы можете превратить проверенное исключение в непроверенное, заключая его в тип RuntimeException и перебрасывая его.

2 голосов
/ 06 мая 2010

В вашем случае это будет Exception s вплоть до до корня стека вызовов. Если объявлен метод для выброса Exception (что очень редко должны делать методы), вызывающий метод должен будет либо сказать, что он также выбрасывает Exception, либо перехватить его и обработать.

Edit Что касается примера в отредактированном OP, он не скомпилируется. Вы можете объявить main, чтобы бросить Exception, если вы не хотите иметь с этим дело.

0 голосов
/ 06 мая 2010

Возможно ли, что ваш компилятор не жалуется на проблему в main(), потому что он решает проблему в method2() и останавливает проверку синтаксиса в этой точке?Оба должны быть ошибкой.Вы исправили вызов в method2() и получили чистую компиляцию?

...