2010-08-04 5 views
2

Как такой Java фрагмент кода:исключение ручки или исключение бросить в Java

public void func() throws XXXException { // throw exception to outer body ------ (2) 
    try { 
     ...... 
    } catch(XXXException ex) { 
     // handle exception ------ (1) 
    } 
} 

В этом состоянии, как вы решили выбрать (1) или (2)? Есть ли какие-либо принципы в обработке исключений Java?

+1

'} catch (ThisQuestionMustHaveBeenAskedBeforeException e) {searchForExamples();}' – akf

ответ

2

Если код, вызывающий метод, который генерирует исключение, может правильно обработать исключение, то он должен его поймать. Если он не может справиться с исключением, он должен бросить его.

Например, если «func» представляет собой низкоуровневый сетевой код, он должен, вероятно, вызывать исключение, а не ловить его. Код, который ультимативно его ловит, должен вывести пользователю сообщение об ошибке (или что-то еще имеет смысл). Если вместо этого «func» является частью уровня GUI, он, вероятно, поймает исключение и отобразит сообщение об ошибке пользователю (или что-то еще имеет смысл).

1

Если вы справитесь с этим, вы справитесь с этим. Например, если вы загружаете файл свойств и получаете FileNotFoundException, возможно, вы можете использовать некоторые свойства по умолчанию. В этом случае вы обрабатываете исключение.

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

Если вы не можете справиться с этим, и вы не хотите вводить сложность исключения исключения, вы должны отправить исключение в службу обработки исключений, которую вы можете настроить во время выполнения. Таким образом, когда модуль тестирования службы обработки исключений может принять это исключение и восстановить его как исключение во время выполнения, которое немедленно завершит крах теста. Однако в производственном коде служба обработки исключений может просто регистрировать исключение и как-то попробовать и перезапустить программу.

0

Вы выбираете (1), если хотите что-то сделать для исключения (например, зарегистрировать его, извлечь информацию из него). Это также часто бросить исключение в блоке поймать после того, как вы сделали с ним (т.е. throw ex;)

Вы выбираете (2), если вы хотите, чтобы пользователи вашего метода обрабатывать его (например, Java's String.matches method)

0

В ореховая оболочка, выберите исключение для внешнего тела, если у вас нет конкретной причины, чтобы поймать исключение.

0

На сайте O'Reilly java есть отличная article об этой теме. В деталях речь идет о том, когда вы должны ловить против броска, а также другие вещи, например, проверенные или исключенные исключения.

0

Исключения представляют собой условия ошибки. Когда возникает условие ошибки, какой-либо метод в цепочке вызовов знает как обрабатывать эту ошибку в контексте приложения т.е. что делать - игнорировать, повторять, прерывать и т. Д. Если это , то метод, который знает как справиться с этим исключением, тогда вы обрабатываете его здесь. Если нет, вы бросаете его так, чтобы метод на один уровень вызывал цепочку, и он принимал его.

Иногда вы можете делать как (1), так и (2). Вы можете обработать исключение, выполнить некоторую промежуточную обработку, а затем восстановить ее.

public void func() throws XXXException { 
    try { 
     ...... 
    } catch(XXXException ex) { 
     logger.log(ex); 
     throw ex; 
    } 
} 

Или вы можете поймать одно исключение и бросить другой, например, когда вы хотите, чтобы обернуть исключение третьей стороной в исключение приложения.

public void func() throws YYYException { 
    try { 
     ...... 
    } catch(XXXException ex) { 
     throw new YYYException(ex); 
    } 
} 

В обоих случаях, это не метод, который полностью обрабатывает исключение и только делает некоторую обработку по пути как исключение просачивается к вершине.

+0

Log rethrow почти никогда не является хорошей идеей. Это приводит к загроможденным журналам с дублированными стеками стека. Я не уверен, какая другая промежуточная обработка есть, кроме очистки (должна быть в конечном итоге) и обработки исключения (не должна быть повторного). – ILMTitan

+0

Согласен. Я использовал его, чтобы продемонстрировать случай броска. Может быть выбран плохой пример. Если это когда-либо требуется для этого, то, что нужно будет сделать внутри улова, будет руководствоваться требованиями приложения. Например, вам может потребоваться отбросить что-то назад и отбросить исключение, чтобы дать вызывающему абоненту возможность реагировать. – samitgaur

+0

Я бы предположил, что catch-and-rethrow-as-something-else, вероятно, подходит, по крайней мере, так часто, как позволяет исключение пузырей; слишком плохо, что нет четкого декларативного способа его указать (язык, который позволяет легко делать не то, что нужно, и все сложнее поправить, побуждает программистов поступать не так). Я бы предположил, что метод должен позволить только проверенному исключению пузыриться от вызываемого метода, если он ожидает, что вызываемый метод может бросить его в условиях, когда вызывающий объект будет связан с этим исключением. – supercat

Смежные вопросы