我想做这样的事情
void DoSomething<T>(T param)
{
if param is IEnumerable<?>
{
loop param and do stuff
}
}
我不知道在问号的地方该怎么做。这有可能吗?
您正在寻找的是:
if (T is IEnumerable) { .. }
但是如果您希望 T 始终是 IEnumerable ,您可以这样做:
void DoSomething<T>(T param) where T : IEnumerable
{
foreach (var t in param) { ... }
}
或检查 IEnumerable 中值的类型:
public void DoSomething<T,U>(T val) where T : IEnumerable<U>
{
foreach (U a in val)
{
}
}
无需担心自己检查,编译器会为您完成,这是拥有静态类型系统和编译器的好处之一 :)
有几种方法:
void DoSomething<T>(T param)
{
if (param is IEnumerable)
{
foreach (var item in (IEnumerable)param)
{
// Do something
}
}
}
void DoSomething<T>(T param)
{
if (param is IEnumerable<string>)
{
foreach (var item in (IEnumerable<string>)param)
{
// Do something
}
}
}
void DoSomething<T,TItem>(T param)
{
if (param is IEnumerable<TItem>)
{
foreach (var item in (IEnumerable<TItem>)param)
{
// Do something
}
}
}
您必须检查该类实现的每个接口的开放泛型类型,如下所示:
bool implements = typeof(T).GetInterfaces().Where(t => t.IsGenericType &&
t.GetGenericTypeDefinition() == typeof(IEnumerable<>)).Any();
这将允许您在IEnumerable<T>
不知道类型是什么的情况下确定类型是否实现T
。请记住,该类型可以实现IEnumerable<T>
多次。
如果您只是想要作为类型参数的类型序列IEnumerable<T>
,您可以将上述查询更改为;
IEnumerable<Type> types = typeof(T).GetInterfaces().
Where(t => t.IsGenericType &&
t.GetGenericTypeDefinition() == typeof(IEnumerable<>)).
Select(t => t.GetGenericArguments()[0]);