Можно ли попробовать / поймать что-то, чтобы просто проверить, было ли выброшено исключение или нет? - PullRequest
51 голосов
/ 10 сентября 2010

Это хороший способ попробовать что-то бесполезное, просто чтобы увидеть, выбрасывает ли конкретное исключение этот код?
Я хочу что-то сделать, когда выдается исключение, и ничего другого.

try {  
    new BigDecimal("some string"); // This do nothing because the instance is ignored  
} catch (NumberFormatException e) {  
    return false; // OK, the string wasn't a well-formed decimal  
}  
return true;

Слишком много предварительных условий для тестирования, и конструктор BigDecimal () всегда проверяет их все, так что это кажется самым простым методом.

Ответы [ 10 ]

49 голосов
/ 10 сентября 2010

Как правило, этой практики следует избегать. Но так как нет никакого служебного метода isValidBigDecimal(..), это путь.

Как отметил Питер Тиллеманс в комментариях, поместите этот код в служебный метод с именем isValidBigDecimal(..). Таким образом, ваш код не зависит от способа определения достоверности, и вы можете даже позже переключиться на другой метод.

Борис Павлович предложил вариант проверить это с помощью сторонней библиотеки (commons-lang). Там есть еще один полезный метод, который я использую всякий раз, когда мне нужно проверить числа - NumberUtils.isNumber(..)

30 голосов
/ 10 сентября 2010

Если вам не нравится такой метод, попробуйте использовать BigDecimalValidator из Apache Commons Validator . В случае неверного ввода String возвращается null.

6 голосов
/ 10 сентября 2010

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

5 голосов
/ 10 сентября 2010

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

(Обратите внимание, что этот конкретный тип преобразования в и из строк действительно предназначен для отладки и внутренней конфигурации. Он не обрабатывает локали и другиеориентированный на человека. Использование в форматах файлов и проводных протоколах вносит сильную зависимость в представление, используемое классом.)

4 голосов
/ 10 сентября 2010

Существует два известных метода «проверки» предварительных условий.

ЛБИЛ: Смотри, прежде чем прыгнуть

Этот стиль кодирования явно проверяет предварительные условия перед выполнением вызовов или поисков. Этот стиль отличается от подхода EAFP и характеризуется наличием множества операторов if.

EAFP: Проще просить прощения, чем разрешения.

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

EAFP - это всегда хорошая идея для языка, в котором есть утка.

Это явно зависит от того, что вы хотите сделать ... Если вы не уверены в том, с каким объектом манипулировать, используйте EAFP.

1 голос
/ 10 сентября 2010

Блоки Try / Catch никогда не должны использоваться для логики.

1 голос
/ 10 сентября 2010

Комментарий к ответу Крисса: я не вижу здесь "превосходной утечки памяти".Нет ссылки на созданный BigDecimal.Как только этот метод завершается, и мы выходим из области видимости, объект пригоден для сборки мусора.

Утечки памяти происходят, когда мы храним ссылки, которые нам больше не нужны, поэтому объект не может быть собран мусором.

1 голос
/ 10 сентября 2010

Да, это, конечно, противоречит идее Прагматического программиста «Исключения для исключительных случаев», но вы понимаете, что делаете, поэтому проблем нет IMO

0 голосов
/ 29 июня 2011

Вы должны учесть, что строительство объекта Exception обходится дорого с точки зрения времени и ресурсов для JVM, потому что оно должно создавать трассировку трассы.

Так что выПредложение - это простой, но ресурсоемкий способ решения проблемы.

То, насколько приемлемо это решение или нет, зависит от использования, которое вы собираетесь использовать для этой функции, и ваших требований к эффективности.

0 голосов
/ 15 сентября 2010

Конечно, почему бы и нет. Это то, что мы делаем, чтобы проверить, правильно ли отформатирован адрес электронной почты, указанный клиентом:

try
{
    MailMessage m = new MailMessage(from, to, subject, body);
    return true;
}
catch(SmtpFailedRecipientsException ex)
{
    return false;
}

Теперь люди могут спорить о производительности или целесообразности структуры, но они забывают о компромиссах в простоте:

  • Выше кода будет ловить ТОЧНЫЕ форматы данных, принятые .NET. Любой, кто проанализировал адреса электронной почты, будет знать, что существует много различий в том, что считается правильно отформатированной структурой адресов электронной почты. Этот код гарантирует проверку структуры адресов электронной почты так, как нравится .NET, а не так, как я думаю.
  • Исключение ловит несколько вариантов использования, а не только правильность базовой структуры данных. Он будет проверять нескольких пользователей в полях CC, BCC и TO, что становится громоздким из-за рукописного кода.

Как уже обсуждали другие, этот код лучше всего абстрагировать в отдельный служебный класс, а не смешивать с вашим основным кодом.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...