如何根据存储在变量中的类型从集合中过滤项目

How to filter items from collection based on type stored in variable

我有以下层次结构:

class Animal

class Dog : Animal

class Cat : Animal

我有一个 List<Animal> 集合,想创建一个方法来 return 所有猫或所有狗。但是我不知道如何根据类型变量过滤列表元素。所以像这样:

int AnimalsOfType(Type animalType)
{
    // Gives error "animalType is a variable but is used like a type".
    return animals.OfType<animalType>().Count;
}
using System.Linq;

int AnimalsOfType(Type animalType)
{
    return animals.Count(a => a.GetType() == animalType);
}

此处最有效的方法是使用 MakeGenericMethodCreateDelegate 创建泛型方法的委托。您可以将这些委托缓存在字典中

static Dictionary<Type, Func<List<Animal>, int>> _methods = new Dictionary<Type, Func<List<Animal>, int>>();

static int CountOfType<T>(List<Animal> source) =>
    source.Count(a => a is T);  
    
int AnimalsOfType(List<Animal> animals, Type animalType)
{
    if(!_methods.TryGetValue(animalType, out var dlgt))
    {
        dlgt = (Func<List<Animal>, int>)
             this.GetType().GetMethod("CountOfType")
                  .MakeGenericMethod(animalType)
                  .CreateDelegate(typeof(Func<List<Animal>, int>)));
        _methods[animalType] = dlgt;
    }
    return dlgt(animals);
}

第一次调用此方法时,每种类型的启动成本很小。