Подтвердить что ты не робот

InvalidArgumentException vs UnexpectedValueException

Когда следует использовать InvalidArgumentException и когда UnexpectedValueException? Они выглядят одинаково для меня.

Обратите внимание на, что один расширяет LogicException, а другой расширяет исключение RuntimeException, поэтому разница не должна быть такой тонкой IMO.

4b9b3361

Ответ 1

Внимательно изучая описания страниц руководства:

InvalidArgumentException:

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

(Примечание: "тип" первоначально был "значением" на странице руководства, что делает его более важным для проверки, чем проверка типов, и более точно соответствует терминологии UnexpectedValueException.)

UnexpectedValueException:

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

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

Ответ 2

Я понимаю, что InvalidArgumentException, будучи LogicException, должен использоваться, если вы проверите аргумент против фиксированного списка возможных диапазонов значений. Например, проверка наличия введенных пользователем данных содержит только числа. Можно ожидать, что программная логика будет обрабатывать эти диапазоны значений.

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

Ключом к ответе на этот вопрос может быть Unexpected... в UnexpectedValueException. Unexpected означает, что для этого значения в логике программы нет обработки. Invalid, с другой стороны, предполагает, что это значение было обработано.

Ответ 3

Я думаю, что наибольшая разница - это "аргумент" против "значения".

Я вижу, что InvalidArgumentException является аргументом (переданным), тогда как UnexpectedValueException применяется к (возвращенным) значениям. Также есть тонкое, но важное различие между "недействительным" и "неожиданным", что также объясняет, почему первым является LogicException, а второе - исключение RuntimeException.

Например: скажем, у меня есть функция, которая использует Twitter-api: getLastMessageDate($userid): Вы передаете (числовой) идентификатор пользователя и возвращает дату последнего сообщения этого пользователя в виде строки yyyy-mm-dd.

Теперь предположим, что я вызываю эту функцию со строкой как аргументом вместо числа. На этом этапе я могу вызвать InvalidArgumentException, потому что предоставленный аргумент недействителен для этой функции. Эти проверки могут выполняться логикой - потому что переменная является либо числовой, либо нет. Поэтому это логическое исключение.

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

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

Теперь представьте, что ребята из Twitter сделали что-то не так, и вместо ожидаемой строки даты yyyy-mm-dd я получаю пустую строку или другую строку с надписью "blaaaa". На этом этапе я могу выбросить UnexpectedValueException.

Я не могу сказать, что это значение "Недопустимо" - я попросил строку, и я получил строку. Но это, однако, не "тип строки", который я ожидал: поэтому Неожиданное ValueException.

Надеюсь, что это что-то прояснит. Это мой первый пост - до сих пор я узнал, что записывать то, что в моей голове - не самая легкая вещь (также английский не мой родной язык).