[英]Referencing instances of Generic Type without knowing the Type
我有一个像这样的通用类:
public class Foo<T>
{
public string SomeMethod();
...
}
我希望存储对这种类型的不同通用实例的引用列表。 例如
List<Foo<object>> foos = new List<Foo<object>>();
foos.Add(new Foo<string>());
foos.Add(new Foo<int>());
foos.Add(new Foo<Person>());
// Then do some processing like ...
foreach (var Foo<object> in foos)
{
Console.WriteLine(foo.SomeMethod());
}
etc...
foos上的编译器错误。添加呼叫说:
"Cannot convert from 'Foo<string>' to 'Foo<object>'
如何存储类型不同的泛型类型实例的列表?
我不想只存储对象列表(ArrayList,List,List等),而不必使用反射来访问其成员!
该T
在Foo<T>
不需要到DoSomething()
因此,您可以通过为DoSomething()
创建接口并将对象存储在该接口的List<>
中来轻松解决问题:
public interface ISomethingDoer {
void DoSomething();
}
public class Foo<T> : ISomethingDoer {
public void DoSomething() { }
}
还有-
List<ISomethingDoer> foos = new List<ISomethingDoer>();
foos.Add(new Foo<string>());
foos.Add(new Foo<int>());
foos.Add(new Foo<Person>());
// Then do some processing like ...
foreach (var foo in foos)
{
Console.WriteLine(foo.DoSomething());
}
您想要创建一个新接口,并将SomeMethod()放入其中,然后让您的泛型实现它。 这是最简单的解决方案。 这就是为什么它们存在。
如果您的SomeMethod依赖于T,那么您需要研究接口协方差和协方差。
class Program
{
public interface IFoo
{
void DoSomething();
}
public interface IGenericFoo<out T> : IFoo
{
T GetDefault();
}
public class Foo<T> : IGenericFoo<T>
{
public T GetDefault()
{
return default(T);
}
public void DoSomething()
{
Console.WriteLine("Meep!");
}
}
private static void Main()
{
var fooCollection = new List<IFoo>
{
new Foo<string>(),
new Foo<StringBuilder>(),
new Foo<int>()
};
foreach (var instance in fooCollection)
instance.DoSomething();
// Covariance example
var fooCollectionGenericI = new List<IGenericFoo<object>>
{
new Foo<string>(),
new Foo<StringBuilder>(),
// new Foo<int>() not possible since covariance is not supported on structs :(
};
foreach (var instance in fooCollectionGenericI)
{
var wxp = instance.GetDefault();
Console.WriteLine(wxp == null ? "NULL" : wxp.ToString());
}
Console.ReadLine();
}
}
在某些情况下,此协方差可能非常有用。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.