I am currently working on code that is using dynamic-linq, I ran into a problem when using a List<BaseClass>, where the list actually contains a list of the Person Class.
When I execute the following code I get a ParseException:
var list = new List<BaseClass>();
list.Add(new Person
{
FirstName = "Joe",
Surname = "Bloggs"
});
list.Where("FirstName == @0", "Joe");
And the Exception:

Please see BaseClass below:
public class BaseClass
{
public int Id { get; set; }
}
And the Person class:
public class Person : BaseClass
{
public string FirstName { get; set; }
public string Surname { get; set; }
}
I can overcome the error by implementing the following code:
var list = new List<BaseClass>();
list.Add(new Person
{
FirstName = "Joe",
Surname = "Bloggs"
});
var newList = CreateListOfCorrectType<BaseClass>(list);
newList.Where("FirstName == @0", "Joe");
Please see CreateListOfCorrectType<T> method below:
private IList CreateListOfCorrectType<T>(
List<T> list)
{
if (list.Count == 0)
{
return list;
}
var typeInfo = list.FirstOrDefault().GetType();
var correctListType = typeof(List<>).MakeGenericType(typeInfo.UnderlyingSystemType);
var listOfCorrectType = (Activator.CreateInstance(correctListType)) as IList;
list.ForEach(x => listOfCorrectType.Add(x));
return listOfCorrectType;
}
My Question is if using the CreateListOfCorrectType is the best way of overcoming the issue? and if not what alternatives do I have in getting the List<BaseClass> to the correct Type.
I am looking to use this with existing code, and changing the existing List<>types are not possible. And the CreateListOfCorrectType method is not aware of the Person class.
Please note that class names and variables are for demonstrative purposes only.
UPDATE
Optimist's answer below leaded me to the solution for my issue, please see extension method used below:
public static IList ToDerivedListType(this IList list)
{
if (list == null || list.Count == 0)
{
return list;
}
var type = list.Cast<object>().FirstOrDefault().GetType();
var castedList = typeof(Enumerable).GetMethod("Cast", System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.Public)
.MakeGenericMethod(type)
.Invoke(null, new[] { list });
return typeof(Enumerable).GetMethod("ToList", System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.Public)
.MakeGenericMethod(type)
.Invoke(null, new[] { castedList }) as IList;
}
System.Linq.Enumerable.Cast and MakeGenericMethod was the key.
depending on the actual use cases, some things can be improved:
CreateListOfCorrectTypefunction copies all elements into a new collection which results in unnecessary expense in case only a subset is taken out of the returned collection .IEnumerable.System.Linq.Enumerable.CastandMakeGenericMethodcan be employed to achieve that:If tried to mimic the function you showed in terms of exceptions thrown. There is a difference because the casting is done after the mapping function returns.