我有一个看起来像这样的方法:
private IEnumerable<T> QueryCollection<T>() where T : BaseObj
{
IEnumerable<T> items = query<T>();
return items;
}
我现在有一种情况,我想过滤这个项目集合,如果&#34; T&#34;支持某个界面(可能不是这样我不能简单地将其添加为T的约束)。所以我想要这样的事情:
private IEnumerable<T> QueryCollection<T>() where T : BaseObj
{
IEnumerable<T> items = query<T>();
if (typeOf(T).GetInterface(ITeamFilterable) != null)
{
items = FilterByTeams(items);
}
return items;
}
检查我的泛型类型是否支持某个接口**的推荐方法是什么?然后如果是,则
注意: FilterByTeams接收:
IEnumerable<ITeamFilterable>
AND返回
IEnumerable<ITeamFilterable>
我是否需要将集合转换2次(一次转换为接口列表然后再转换回T列表?)
答案 0 :(得分:1)
我担心在这种情况下您无法使用is
/ as
,除非您可以开始枚举查询。
您可以使用这样的反射:
private IEnumerable<T> QueryCollection<T>() where T : BaseObj
{
IEnumerable<T> items = query<T>();
if (typeof(ITeamFilterable).IsAssignableFrom(typeof(T)))
items = (IEnumerable<T>)(object)FilterByTeams(items.Cast<ITeamFilterable>());
return items;
}
但是如果你可以枚举查询,你可以这样做以避免反思(假设你没有null
个项目):
private IEnumerable<T> QueryCollection<T>() where T : BaseObj
{
IEnumerable<T> items = query<T>();
ICollection<T> itemsCollection = items as ICollection<T> ?? items.ToList();
if (itemsCollection.Count > 0)
{
var firstItem = itemsCollection.First();
if (firstItem is ITeamFilterable)
return (IEnumerable<T>)(object)FilterByTeams(itemsCollection.Cast<ITeamFilterable>());
}
return itemsCollection;
}
由于ITeamFilterable
是T
并且IEnumerable<T>
是协变的,所以强制转换是有效的,但您必须强制转换为object
以满足泛型约束。使用这些演员表,不需要复制项目。