#c# #generics
#c# #обобщения
Вопрос:
Я пытаюсь вернуть объект класса, используя дженерики.
Это универсальный класс
public class ClientBase <S>
{
protected S CreateObject()
{
return default(S) ;
}
}
Вот как я пытаюсь это использовать…
public class ClientUser : ClientBase <SomeClass>
{
public void call()
{
var client = this.CreateObject();
client.SomeClassMethod();
}
}
Хотя я получаю объект SomeClassMethod()
в объекте клиента, при запуске кода он выдает ошибку в строке:
клиент.SomeClassMethod();
Ошибка: «Ссылка на объект не установлена для экземпляра объекта». Я знаю, что в методе CreateObject() клиентской базы универсального класса чего-то не хватает; просто не могу понять это. Может ли кто-нибудь помочь мне здесь, пожалуйста?
Спасибо за ваше время…
Ответ №1:
default(S)
где S
ссылочный тип равен нулю. В вашем случае default(SomeClass)
возвращает значение null. Когда вы пытаетесь вызвать метод по нулевой ссылке, именно тогда вы получаете свое исключение.
Вы пытаетесь вернуть экземпляр по умолчанию SomeClass
? Возможно, вы захотите использовать new()
ограничение и return new S()
вместо этого в своем универсальном классе, например:
public class ClientBase<S> where S : new()
{
protected S CreateObject()
{
return new S();
}
}
Если S
необходимо указать ссылочный тип, вы также можете ограничить его class
:
public class ClientBase<S> where S : class, new()
{
protected S CreateObject()
{
return new S();
}
}
Комментарии:
1. отредактировал мой вопрос … пропустил фактическую ошибку. 🙂
2. да, пытаюсь вернуть экземпляр. Я попробовал то, что вы положили. теперь я понимаю это… Целью вызова было вызвано исключение.
3. @user20358: Вполне вероятно, что какой-то другой код в вашей программе вызывает такое исключение.
4. @user20358: проверьте InnerException исключения TargetInvocationException на наличие фактического исключения
Ответ №2:
Посмотрите, что default(T)
делает: http://msdn.microsoft.com/en-us/library/xwth0h0d.aspx
В вашем случае default(S)
будет возвращено значение null (потому что это класс) — это не экземпляр класса.
Вам нужно либо вызвать new S()
какой-либо другой S
конструктор, либо переопределить CreateObject
его в вашем производном классе.