como - consultas en c#
LINQ: De una lista de tipo T, recupere solo objetos de una cierta subclase S (4)
Dada una jerarquía de herencia simple: Persona -> Estudiante, profesor, personal
Digamos que tengo una lista de Personas, L. En esa lista hay algunos estudiantes, maestros y personal.
Usando LINQ y C #, ¿hay alguna manera de escribir un método que pueda recuperar solo un tipo particular de persona?
Sé que puedo hacer algo como:
var peopleIWant = L.OfType< Teacher >();
Pero quiero poder hacer algo más dinámico. Me gustaría escribir un método que recupere resultados para cualquier tipo de Persona que pudiera pensar, sin tener que escribir un método para cada tipo posible.
Esto debería funcionar.
var students = persons.Where(p => p.GetType() == typeof(Student));
Para lista general, usar delegate
:
public List<T> FilterByType(List<T> items, Type filterType)
{
return items.FindAll(delegate(T t)
{
return t.GetType() == filterType;
});
}
Podrías hacer esto:
IEnumerable<Person> GetPeopleOfType<T>(IEnumerable<Person> list)
where T : Person
{
return list.Where(p => p.GetType() == typeof(T));
}
Pero todo lo que realmente ha hecho es volver a escribir el método OfType () de LINQ con una versión más segura que utilice la comprobación de tipos estática para asegurarse de que pasa una persona. Aún no puede usar este método con un tipo que se determina en el tiempo de ejecución (a menos que use reflexión).
Para eso, en lugar de usar genéricos, tendrás que hacer que la variable de tipo sea un parámetro:
IEnumerable<Person> GetPeopleOfType(IEnumerable<Person> list, Type type)
{
if (!typeof(Person).IsAssignableFrom(type))
throw new ArgumentException("Parameter ''type'' is not a Person");
return list.Where(p => p.GetType() == type);
}
Ahora puedes construir algún tipo dinámicamente y usarlo para llamar a este método.
Puedes hacerlo:
IList<Person> persons = new List<Person>();
public IList<T> GetPersons<T>() where T : Person
{
return persons.OfType<T>().ToList();
}
IList<Student> students = GetPersons<Student>();
IList<Teacher> teacher = GetPersons<Teacher>();
EDITAR: añade la restricción de donde.