Исключение исключений нулевого указателя
Я прошу об этом в основном о Java, но я думаю, что он подходит для целого ряда языков.
Рассмотрим,
if(myVariable==null){
doSomethingAboutIt();
}
else carryOn(myVariable);
и
try{
carryOn(MyVariable);
}catch(NullPointerException e ){
doSOmethingAboutIt();}
Являются ли оба эти кодовые блоки по существу одинаковыми? Есть ли какая-то причина выбора второго подхода? Конечно, это было бы bette rif myVariable никогда не было нулевым, но кажется, что лучший способ проверить это - сделать простой оператор if.
Ответы
Ответ 1
С моей позиции я не решаюсь рассматривать эти два блока кода, эквивалентные намерениям. Конечно, они выполняют ту же самую обработку ошибок, но это решение разработчика больше, чем что-либо еще.
Для меня if
проверяет, можно ли использовать значение, и если оно не может, оно работает над проблемой. Блок try...catch
предполагает, что значение действительно, а если нет, то он преодолевает отклоняющееся поведение.
Исключения должны быть рассмотрены вначале, когда возникает аберрантный, программный код (деление на ноль и т.д.).
Ответ 2
Нет, эти кодовые блоки не совпадают.
В первом блоке кода вы проверяете, есть ли myVariable
null
, и вы делаете это только в один момент времени. Позже myVariable
может стать null
и в итоге выбросить NullPointerException
. Если это произойдет, второй фрагмент кода поймает исключение, но первое не будет.
Кроме того, второй фрагмент кода поймает NullPointerExceptions
, который может быть выброшен из любого места в стеке вызовов, вызванный вызовом carryOn(myVariable)
. Это ужасно; вы проглатываете исключение, действуя в предположении, что конкретная переменная null
, когда она может быть чем-то совсем другим.
Используйте первый фрагмент кода.
Ответ 3
Ну, сам по себе carryOn(MyVariable);
никогда не будет бросать NPE, если только что-то в carryOn
не ссылается на вызов метода или свойства в нулевом экземпляре.
Захват исключений является более вычислительно дорогостоящим, чем первая проверка для него, поскольку для генерации исключения требуется создание трассировки стека и т.д.
Я бы сказал, что он также приводит к "более чистым" кодам.
См. также:
- Java try/catch performance, рекомендуется ли сохранить то, что находится в предложении try до минимума?
- Попробуйте Catch Performance Java
Ответ 4
Вы используете исключения только для исключительных случаев. Пойдите с первым блоком кода, а не вторым.
Ответ 5
Первый подход лучше, чем исключение catching, потому что есть некоторые нарушения производительности. На мой взгляд, лучший подход - применить шаблон Null Object. Библиотека Guava предоставляет Optional класс, который можно использовать вместо создания собственного.