В этом посте я расскажу об ошибке, которую я встречал довольно часто, и которая может привести к тем уродливым исключениям « ссылка на объект не установлена на экземпляр объекта ».
Вот вопрос. В чем разница между следующими 2 фрагментами кода?
var result = controller.Login() as ViewResult;
var result = (ViewResult)controller.Login();
Во время просмотра одного из видеороликов Mix 09 я видел довольно известного разработчика, который использовал первый тип приведения, когда он явно искал поведение второго. (Я не буду упоминать, кто это был)
Так в чем же разница? Если объект возвращается из Логина вызова метода (который является ActionResult в данном случае) действительно является экземпляром ViewResultкласса, как фрагменты будут вести себя точно так же. Однако, если приведение недопустимо (например, если возвращенный объект — RedirectToRouteResult ), первый фрагмент установит для объекта результата значение null , а второй — для исключения InvalidCastException .
Итог — если вы ожидаете, что объект будет определенного типа, выполните явное приведение (второй фрагмент). Если вы не уверены в типе объекта, либо проверьте тип, либо выполните безопасное приведение (первый фрагмент) и убедитесь, что результат равен нулю .
Я на самом деле использую это поведение довольно часто при выполнении TDD с MVC — первый тест, который я пишу для действия, обычно проверяет возвращаемое значение.
[Test]
public void LoginActionShouldReturnLoginView()
{
var result = controller.Login() as ViewResult;
Assert.IsNotNull(result);
Assert.AreEqual("Login", result.ViewName);
}
Если бы я тестировал другую часть поведения, я бы просто сделал явное приведение.
Свежие комментарии